优化访问Django中ManyToMany字段的最佳方法是什么?

时间:2011-11-05 16:33:56

标签: django django-models django-queryset

我有一个带有两个ManyToMany字段的Video对象。每个都包含一个用户列表。我想知道优化是多么重要,以便在访问视频时只有一个数据库调用 - 或者甚至有办法实现这一点。另外 - 我只会使用这些ManyToMany字段中的每个字段的数量 - 调用Count()比获得整个列表然后“长度”更“便宜”吗?

例如:

class Video(models.Model):
  ...
  dislikes = models.ManyToManyField(User, null=True)
  likes = models.ManyToManyField(User, null=True)
  ...

在我渲染特定视频对象的模板中 - 我需要计算每个喜欢和不喜欢的内容。什么是性能最佳方式?在我看来,调用count()导致两个额外的db调用是最好的 - 但我不确定...

1 个答案:

答案 0 :(得分:2)

来自文档:

“如果你想要做的只是确定集合中的记录数量,不要在QuerySets上使用len()。使用SQL的SELECT COUNT(*)来处理数据库级别的计数要高效得多,正是出于这个原因,Django提供了一个count()方法。“

您可能还有另一种方法,而不是使用count()作为单独的操作,您可能希望使用喜欢/不喜欢的计数来注释QuerySet。类似的东西:

video = Video.objects.get(id=<video_id>).annotate(num_likes=Count('likes'), num_dislikes=Count('dislikes'))

这将获得包含num_likesnum_dislikes字段的视频对象。您可以使用filter()all()代替get()来获取多个视频,每个视频都有num_likesnum_dislikes字段。在您的模板中,您可以{{ video.num_likes }}{{ video.num_dislikes }}来显示这两个带注释的字段。