繁体   English   中英

Django | 在模板中排序字典

[英]Django | sort dict in template

我想打印出一个字典,按键排序。 通过将键放在列表中然后对列表进行排序,可以在视图中轻松地对键进行排序。 如何循环模板中的键,然后从字典中获取值。

{% for company in companies %}
    {% for employee, dependents in company_dict.company.items %}
    {% endfor %}
{% endfor %}

(刚刚编写的例子......)不起作用的部分是“company_dict.company.items”部分。 我需要“公司”才能成为公司的价值所在。 现在,公司的Prat正在寻找一个名为“公司”的钥匙,而不是上面循环中“公司”的价值。

我正在做一些处理,把字典词典放在一起。 改变数据的布局实际上不是一种选择。 我认为正确的方法是编写模板标签,只是想知道我是否有错过的内置方式。

创建自定义过滤器,如下所示:

from django import template
from django.utils.datastructures import SortedDict

register = template.Library()

@register.filter(name='sort')
def listsort(value):
    if isinstance(value, dict):
        new_dict = SortedDict()
        key_list = sorted(value.keys())
        for key in key_list:
            new_dict[key] = value[key]
        return new_dict
    elif isinstance(value, list):
        return sorted(value)
    else:
        return value
    listsort.is_safe = True

然后在你的模板中你应该使用:

{% for key, value in companies.items|sort %}
      {{ key }} {{ value }}
{% endfor %}

您将能够通过Key获取已排序的词典。

试试这个: http//www.bhphp.com/blog4.php/2009/08/17/django-templates-and-dictionaries

自定义模板过滤器可以解决问题。

from django import template
register = template.Library()

def dict_get(value, arg):
    #custom template tag used like so:
    #{{dictionary|dict_get:var}}
    #where dictionary is duh a dictionary and var is a variable representing
    #one of it's keys

    return value[arg]

register.filter('dict_get',dict_get)

更多关于自定义模板过滤器: http//docs.djangoproject.com/en/dev/howto/custom-template-tags/#howto-custom-template-tags

在你的例子中你会做:

{% for employee, dependents in company_dict|company %}

最后一个解决方案对我也非常有用。 我正在使用Django 1.6.2,它似乎是将一个字典转换为一个列表,其中键作为该列表的第一个元素,内容作为第二个元素。 因此,即使我传入一个词典,它也会将其视为一个列表。 所以我调整了上面的内容,看起来像这样,它对我有用:

@register.filter(name='sort')
def listsort(value):
    if isinstance(value, list):
        return sorted(value, key=lambda k:k[0])
    else:
        return value

对于一些reasone Turikumwe的过滤器对我不起作用(python3.4,Django 1.7),所以我重写它以返回元组列表而不是SertedDictOrderedDict

@register.filter(name='sort')
def listsort(value):
    if isinstance(value, dict):
        a = []
        key_list = sorted(value.keys())
        for key in key_list:
            a.append((key, value[key]))
        return a
    elif isinstance(value, list):
        return sorted(value)
    else:
        return value

listsort.is_safe = True

所以在模板中我们不需要得到.items

{% for key, value in companies|sort %}
      {{ key }} {{ value }}
{% endfor %}

Turikumwe的回答让我很接近,但是对我的环境不起作用:python3和Django 1.10。

我发现用以下方法调用过滤器:

{% for key, value in companies.items|sort %}
      {{ key }} {{ value }}
{% endfor %}

实际上会产生一个ItemsView对象,而不是一个dict。 (我怀疑这是一个python 2 vs 3的问题)。 鉴于ItemsView,答案更容易

from django import template
from django.utils.datastructures import ItemsView

register = template.Library()

@register.filter(name='sort')
def listsort(value):
    if isinstance(value, ItemsView) or isinstance(value, list):
        return sorted(value)
    else:
        return value

你可以使用django的dictsortdictsortreversed

{% for user in list_users|dictsort:'created_at' %}
    {{user.username}} - {{user.created_at}}
{% endfor %}

要么

{% for user in list_users|dictsortreversed:'created_at' %}
    {{user.username}} - {{user.created_at}}
{% endfor %}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM