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

在Django中关联两个模型并按产品名称分组求和(含金额计算)

解决方案

你需要通过Django的聚合函数和F()表达式实现关联模型分组、数量求和及总金额计算,以下是具体实现步骤:

修改视图代码

from django.db.models import Sum, F
from django.shortcuts import render

def stockPrice(request):
    # 关联产品详情,按产品分组统计库存并计算各类总金额
    stock = InventorySummary.objects.select_related('product_name')\
            .values(
                'product_name__id', 
                'product_name__product_name',
                'product_name__purchase_price',
                'product_name__dealer_price',
                'product_name__retail_price'
            )\
            .annotate(total_quantity=Sum('quantity'))\
            .annotate(
                total_purchase=Sum('quantity') * F('product_name__purchase_price'),
                total_dealer=Sum('quantity') * F('product_name__dealer_price'),
                total_retail=Sum('quantity') * F('product_name__retail_price')
            )

    return render(request, 'inventory_price.html', {'stock': stock})

代码说明

  • select_related('product_name'):提前关联ProductDetails模型,避免多次查询数据库的N+1问题
  • values():指定需要返回的产品核心字段,通过双下划线__关联外键模型的属性
  • annotate(total_quantity=Sum('quantity')):按产品分组后统计该产品的总库存数量
  • 第二个annotate:用F()表达式将求和后的库存数量与对应价格字段相乘,直接在数据库层面计算出不同定价下的总金额

模板渲染示例(inventory_price.html)

<table>
    <thead>
        <tr>
            <th>产品名称</th>
            <th>总库存数量</th>
            <th>采购总价</th>
            <th>经销商总价</th>
            <th>零售总价</th>
        </tr>
    </thead>
    <tbody>
        {% for item in stock %}
        <tr>
            <td>{{ item.product_name__product_name }}</td>
            <td>{{ item.total_quantity }}</td>
            <td>{{ item.total_purchase|floatformat:2 }}</td>
            <td>{{ item.total_dealer|floatformat:2 }}</td>
            <td>{{ item.total_retail|floatformat:2 }}</td>
        </tr>
        {% endfor %}
    </tbody>
</table>

可选命名优化建议

你的InventorySummary模型中外键字段命名为product_name易造成混淆(实际关联的是整个产品对象而非名称),建议修改为product,更符合Django规范:

class InventorySummary(models.Model):
    id = models.AutoField(primary_key=True)
    date = models.DateField(default=date.today)
    product = models.ForeignKey(ProductDetails, on_delete=models.CASCADE, related_name='inventory')
    quantity = models.IntegerField()

    def __str__(self):
        return str(self.product)

修改后视图中的关联字段需对应调整,比如select_related('product')、values('product__product_name')等,可提升代码可读性。

内容的提问来源于stack exchange,提问作者Shanzedul

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 17:45:39