如何在Django中按分组查询?

2024-04-25 19:02:00 发布

您现在位置:Python中文网/ 问答频道 /正文

我查询模型:

Members.objects.all()

它返回:

Eric, Salesman, X-Shop
Freddie, Manager, X2-Shop
Teddy, Salesman, X2-Shop
Sean, Manager, X2-Shop

我想知道最好的射击方法 对我的数据库的一个group_by查询,例如:

Members.objects.all().group_by('designation')

当然,这不管用。 我知道我们可以在django/db/models/query.py上做一些技巧,但我只是想知道如何在不打补丁的情况下做到这一点。


Tags: 方法模型byobjectsgroupmanagerallshop
3条回答

还可以使用regroup模板标记按属性分组。从文档中:

cities = [
    {'name': 'Mumbai', 'population': '19,000,000', 'country': 'India'},
    {'name': 'Calcutta', 'population': '15,000,000', 'country': 'India'},
    {'name': 'New York', 'population': '20,000,000', 'country': 'USA'},
    {'name': 'Chicago', 'population': '7,000,000', 'country': 'USA'},
    {'name': 'Tokyo', 'population': '33,000,000', 'country': 'Japan'},
]

...

{% regroup cities by country as country_list %}

<ul>
    {% for country in country_list %}
        <li>{{ country.grouper }}
            <ul>
            {% for city in country.list %}
                <li>{{ city.name }}: {{ city.population }}</li>
            {% endfor %}
            </ul>
        </li>
    {% endfor %}
</ul>

看起来像这样:

  • 印度
    • 孟买:19000000
    • 加尔各答:15000000
  • 美国
    • 纽约:20000000
    • 芝加哥:7000000
  • 日本
    • 东京:33000000

我相信它也适用于QuerySet

来源:https://docs.djangoproject.com/en/2.1/ref/templates/builtins/#regroup

编辑:注意regroup标记不会像您希望的那样工作,如果您的字典列表不是按键排序的。它迭代工作。因此,在将列表传递给regroup标记之前,请按grouper的键对其进行排序。

如果要进行聚合,可以使用aggregation features of the ORM

from django.db.models import Count
Members.objects.values('designation').annotate(dcount=Count('designation'))

这将生成一个类似于

SELECT designation, COUNT(designation) AS dcount
FROM members GROUP BY designation

结果会是

[{'designation': 'Salesman', 'dcount': 2}, 
 {'designation': 'Manager', 'dcount': 2}]

一个简单的解决方案,但不是正确的方法是使用raw SQL

results = Members.objects.raw('SELECT * FROM myapp_members GROUP BY designation')

另一种解决方案是使用group_by属性:

query = Members.objects.all().query
query.group_by = ['designation']
results = QuerySet(query=query, model=Members)

现在可以遍历results变量来检索结果。注意group_by没有文档记录,可能在Django的未来版本中更改。

还有。。。为什么要使用group_by?如果不使用聚合,可以使用order_by来获得相同的结果。

相关问题 更多 >