首页 > 解决方案 > 如何找到相关对象的相关对象的聚合计数最小计数?

问题描述

我有这样的关系模型:

Parent(models.Model):
    pass

Child(models.Model):
   parent = models.ForeignKey(Parent, on_delete=models.CASCADE)

Grandchild(models.Model):
   child = models.ForeignKey(Child, on_delete=models.CASCADE)

我试图找到一种方法来用孙子的总数来注释父查询集。

例如,假设 2 位父母:(A, B). A有3个孩子:(A.a, A.b, A.c)A.a有1个孙子, A.b有2个孙子, A.c有3个孙子, B有2个孩子:(B.a, B.b). B.a有2个孙子。 B.b有3个孙子。

我想用每个父母上每个孩子的孙子计数的聚合来注释父查询集。例如,聚合与Min将是A:1, B:2或聚合与Avg将是A:2, B:2.5

我相信这可能需要.extra完成,但我不确定。

如果聚合函数是硬编码的,那很好Parent.objects.all().annotate_min_ngc_per_c(),但请尽可能解释,我可以用多个聚合重现。

标签: djangodjango-models

解决方案


获得 Min 或 Max 的一种解决方案是使用这样的 SubQuery:

counts = Child.objects.filter(parent=OuterRef('pk'))
counts = counts.annotate(num_grandchildren=Count('grandchild_set'))
counts = counts.order_by('-num_grandchildren').values('num_grandchildren')[:1]
qs = Parent.objects.annotate(min_num_grandchildren=Subquery(counts))

它不是聚合的,但它会为您提供 Min/Max。


推荐阅读