django 如何聚合两个模型的平均值以在一个模型的字段中使用?

qjp7pelc  于 2023-05-08  发布在  Go
关注(0)|答案(1)|浏览(190)

我有两个模型:

class Review(models.Model):
  artist = models.CharField(max_length=100)
  album = models.CharField(max_length=200)
  rating = models.IntegerField(
    validators=[MinValueValidator(0), MaxValueValidator(10)],
    default=10,
  )
  content = models.TextField(null=True, blank=True)
  updated = models.DateTimeField(auto_now=True)
  created = models.DateTimeField(default=timezone.now)
  author = models.ForeignKey(User, on_delete=models.SET_NULL, null=True)
  ...

class AddedReview(models.Model):
  user = models.ForeignKey(User, on_delete=models.CASCADE)
  review = models.ForeignKey(Review, on_delete=models.CASCADE)
  rating = models.IntegerField(default=10)
  body = models.TextField()
  updated = models.DateTimeField(auto_now=True)
  created = models.DateTimeField(default=timezone.now)
  ...

Review模型是用户发布的初始评论。AddedReview模型是用户可以在初始Review上发布的额外评论。初始Review将由原始用户添加rating,其他用户将添加额外的rating。我希望能够将这两个模型中的所有rating聚合到avg_rating字段中,以便在Review模型中使用。
我知道如何在Python shell中执行此操作,但我不太了解如何创建模型方法来执行此操作。

ldxq2e6h

ldxq2e6h1#

看看这个

class Review(models.Model):
    artist = models.CharField(max_length=100)
    album = models.CharField(max_length=200)
    rating = models.IntegerField(
        validators=[MinValueValidator(0), MaxValueValidator(10)],
        default=10,
    )
    # [...]
  
    def give_avg_rev(self):
        rev = self.rating

        # maybe `.all()` in next line is not neccessary
        add_rev = self.addedreview_set.all().aggregate(Avg('rating'))
        return (rev + add_rev) / 2

class AddedReview(models.Model):
    user = models.ForeignKey(User, on_delete=models.CASCADE)
    review = models.ForeignKey(Review, on_delete=models.CASCADE)
    rating = models.IntegerField(default=10)
    # [...]

阅读更多关于一对多关系的信息。当您有一个Review托管多个AddedReview时,您可以说:一个Review有一组AddedReview s。这将引导你到django的反向查找功能。在链接的网站上搜索“_set”,你会发现更多的例子。
因为你没有告诉你想在哪里使用这个功能,我将展示一个基本的视图:

def my_view(request):
    r = Review.objects.all().first()
    return HttpResponse(f"Average rating is {r.give_avg_rev()}")

让我知道如果这对你有用!

相关问题