【问题标题】:django Count on FK with Sum and filtersdjango Count on FK with Sum 和 filters
【发布时间】:2021-05-05 09:26:13
【问题描述】:

我必须找到两个字段的总和高于给定字段的参与者数量。以下型号:

class Examination(models.Model):
    total_score = models.FloatField(_('Total score'), blank=False, null=False, default=60)

class ExamParticipation(models.Model):
    examination = models.ForeignKey(Examination, blank=False, null=False, on_delete=models.CASCADE, related_name='examination_participations')
    total_score = models.DecimalField(_('examination score'), max_digits=3, decimal_places=1, default=0)
    additional_score = models.DecimalField(_('additional score'), max_digits=3, decimal_places=1, default=0)

因此,对于给定的考试,我必须计算有多少参与者,其中 total_score 和 additional_core 的总和大于或等于 total_score/2。这对于查询集是否可行,还是我必须遍历结果?

我尝试了以下查询:

    def count_sufficient_participations(self):
        qs = self.values('examination_participations').order_by('examination_participations').annotate(
        ts=Sum(F('examination_participations__total_score') + F('examination_participations__additional_score'))
    ).annotate(cnt_suff=Count('examination_participations')).filter(ts__gte=30)

但似乎不起作用,我不知道如何用考试中的字段 total_score 替换 30。我想为我的模板设置像 Exam.cnt_suff 这样的东西。任何帮助将不胜感激。

【问题讨论】:

  • 我发现30可以换成F('total_score') / 2

标签: django django-orm


【解决方案1】:

Sum 是一个aggregate 函数,这意味着保持处理中与查询匹配的列的所有值。

但您想对当前行的第 2 列求和。

所以用

ts = F('examination_participations__total_score') + F('examination_participations__additional_score')

而不是

ts = Sum(F('examination_participations__total_score') + F('examination_participations__additional_score'))

【讨论】:

  • 好的,这是正确的,但这仍然给了我每行的计数。我需要对整个查询集进行计数。
  • @cwhisperer 如果您只需要计数,请使用 ...filter(ts_gte=30).count() 并删除 .annotate(cnt_suff=Count('examination_participations'))
【解决方案2】:

我找到了以下解决方案:

def count_sufficient_participations(self):
    qs = self.annotate(
        cnt_suff=Count('examination_participations', filter=Q(total_score__lte=(F('examination_participations__total_score') + F('examination_participations__additional_score')) * 2))
    )
    return qs

感谢您的帮助。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-10-27
    • 2013-05-07
    • 2022-12-02
    • 1970-01-01
    • 2015-11-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多