【问题标题】:Django Rest Framework regroup queryset by a categoryDjango Rest Framework 按类别重新组合查询集
【发布时间】:2018-09-24 12:24:39
【问题描述】:

在我正在处理的当前项目中,我需要按类别重新组合(分组)一个查询集,并将具有相同类别的内容放在一起提供的列表中。 我有以下模型结构:

class Category(models.Model):
    title = models.CharField(max_length=255)

class Item(models.Model):
   title = models.CharField(max_length=255)
   category = models.ForeignKey(to="Category", verbose_name=_('category'), related_name='items',
                                 on_delete=models.SET_NULL, null=True, blank=True)

我希望输出序列化结果如下:

    {
     "category_title_1":[
        {
          "id": 1,
          "title" : "something",
        },
        {
          "id": 2,
          "title": "something else",
        }
      ],
    "category_title_2": [
      {
       "id": 3,
       "title": "another string",
      }, 
      {
       "id": 4,
       "title": "and yet another title",
      }
    ]
  }  

我知道我总是可以遍历查询集并将它们手动分组,我想知道是否有一种本地有效的方法来做到这一点。

谢谢

【问题讨论】:

  • 如果你要实现类似节点的结构。我建议django-mpttdjango-rest-framework-recursive。对于这类问题,他们有现成的解决方案

标签: python django django-rest-framework grouping serialization


【解决方案1】:

我不相信使用 ORM 本身可以做到这一点,尽管正如 Guybrush 所提到的,itertools.groupby 可以用来实现这一点 - 并且以一种相当优雅的方式。

from itertools import groupby
from operator import itemgetter
from rest_framework.response import Response

items = Item.objects.values('category__title', 'id', 'title').order_by('category__title')
rows = groupby(items, itemgetter('category__title'))
return Response({c_title: list(items) for c_title, items in rows})

【讨论】:

    【解决方案2】:

    如果您的目标是在模板中重新组合它们,请查看 https://docs.djangoproject.com/en/2.0/ref/templates/builtins/#regroup 请注意,您必须首先按类别对对象进行排序,因为regroup 依赖于该顺序来产生正确的输出。

    如果您的目标是在代码中重新组合它们(而不是模板),您可以依赖itertools.groupby(请参阅https://docs.python.org/3/library/itertools.html#itertools.groupby)。同样,您需要先加入数据并对其进行排序。

    【讨论】:

      猜你喜欢
      • 2017-06-04
      • 2016-09-30
      • 2021-05-29
      • 2018-06-17
      • 2020-09-25
      • 1970-01-01
      • 1970-01-01
      • 2014-10-08
      • 2019-03-20
      相关资源
      最近更新 更多