django 中的嵌套 GROUP BY:返回对象

Nested GROUP BY in django: returning Objects

我正尝试在我的 Django 查询集上使用经典数据库 GROUP_BY。

我已经看过 How to query as GROUP BY in django? 但区别是:

我的模型:

class CitiesTable(models.Model):
    country = models.TextField() 
    region_or_state = models.TextField() 
    city = models.TextField() 

我想按 country 分类,然后在其中按 region_or_state 分类,里面有 city:

的列表

我想得到

{'USA':
    {'California': ['San Francisco', 'Los Angeles', ...],
     'Texas': ['Dallas', 'Houston', ...},
 'Germany':
     {'Bavaria': ['Munich', 'Nuremberg', ...}
}

但是在这里,如前所述,列表中的城市应该是 Objects.

我没有找到如何在 Django 中获取它,因此,在 python 中使用 itertools,我已经成功获取了外部 GROUP_BY: (帮助我:How to convert tuple to a multi nested dictionary in python?):

from itertools import groupby

def show_cities(request):
    queryset = CitiesTable.objects.all()
    grouped_cities = []
    unique_countries = []
    for k, g in groupby(queryset, lambda x: x.country):
        grouped_cities.append(list(g))
        unique_countries.append(k)
    return render(request, 'cities/show_cities.html', 
                  {'cities':grouped_cities, 'countries':unique_countries})

但我没能在 region_or_state 中对所有城市对象进行分组。

恐怕我不知道如何用 django 的查询集解决这个问题。可能没有解决方案,或者如果有,可能涉及使用未记录的功能。

但是,python 解决方案在大多数情况下都可以正常工作。无论如何,Django 可能不得不自己做类似的事情。

看起来您当前的代码可能存在一些小问题。在使用 itertools.groupby 之前,您几乎应该总是对您的条目进行排序 - 这是一个常见的陷阱,以至于我很惊讶它不会自动排序。 Groupby 遍历可迭代对象,并在每次键的值发生变化时创建一个新组。因此,要对一个可迭代对象进行完全分组,您需要先按键排序。

这里可以使用数据库进行排序,只需使用两次groupby

queryset = CitiesTable.objects.order_by('country', 'region_or_state')

countries_dict = {}

for country, group in groupby(queryset, lambda x: x.country):
    countries_dict[country] = {}
    for region, inner_group in groupby(group, lambda x: x.region_or_state):
        countries_dict[country][region] = list(inner_group)