You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django Model实现增量累计总和时所有记录返回总数值问题排查

你当前的total_hours方法每次调用都会对全表所有Hours记录执行聚合求和,所以所有实例调用返回的都是全表总小时数,自然不会得到逐行递增的运行累计值。

场景1:保留实例方法写法

如果需要在单个实例上直接调用方法获取累计值,可以按你指定的排序规则(通常用主键id、创建时间等),筛选出排序顺序在当前记录之前(含当前记录)的所有数据再求和,示例代码如下:

from django.db import models
from django.db.models import Sum

class Hours(models.Model):
    name = models.CharField(max_length=200)
    hours = models.DecimalField(max_digits=6, decimal_places=2)

    def running_total_hours(self):
        # 示例按主键id升序排序累计,如需其他排序规则替换过滤条件即可
        return Hours.objects.filter(id__lte=self.id).aggregate(total=Sum('hours'))['total']

场景2:批量查询时更高效的实现

如果是批量查询列表时要获取每条记录的累计值,更推荐用Django的窗口函数在查询时直接注解结果,避免每条记录都单独触发一次数据库查询,性能更高:

from django.db.models import Window, Sum, F

# 按id升序排序,同时注解累计小时数字段
hours_queryset = Hours.objects.order_by('id').annotate(
    running_total = Window(
        expression=Sum('hours'),
        order_by=F('id').asc()
    )
)

# 遍历查询结果直接获取累计值
for hour_obj in hours_queryset:
    print(f"{hour_obj.name}:当前小时数{hour_obj.hours},累计小时数{hour_obj.running_total}")

注意:累计值的计算依赖明确的排序规则,如果你需要按其他字段(比如创建时间、业务编号等)排序累计,替换上述代码中的id为对应字段即可。

内容的提问来源于stack exchange,提问作者Umar Milanzi Snr

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 03:15:02