.items在Django模板中的defaultdict上不起作用
我无法让.items在我的Django模板中工作:
I can't get .items to work in my Django template:
从CBV的get_context_data复制并粘贴:
copy and paste from my CBV's get_context_data:
context['data'] = assertion_dict
context['dataitems'] = assertion_dict.items()
return context
从我的模板复制并粘贴:
copy and paste from my template:
<h3>data dump</h3>
{{data}}
<h3>dataitems</h3>
{% for key, value in dataitems %}
{{ key }}: {{ value }} <br/>
{% endfor %}
<h3>data.items</h3>
{% for key, value in data.items %}
{{ key }}: {{ value }} <br/>
{% endfor %}
<h3>Not found test</h3>
{{ i_dont_exist }}
输出:
**data dump**
defaultdict(<class 'list'>, {<BadgeType: Talent>: [<BadgeAssertion: Blender Blue Belt>], <BadgeType: Achievement>: [<BadgeAssertion: MyBadge#1>, <BadgeAssertion: MyBadge#1>, <BadgeAssertion: MyBadge#2>], <BadgeType: Award>: [<BadgeAssertion: Copy of Copy of Blenbade>]})
**dataitems**
Talent: [<BadgeAssertion: Blender Blue Belt>]
Achievement: [<BadgeAssertion: MyBadge#1>, <BadgeAssertion: MyBadge#1>, <BadgeAssertion: MyBadge#2>]
Award: [<BadgeAssertion: Copy of Copy of Blenbade>]
**data.items**
**Not found test**
DEBUG WARNING: undefined template variable [i_dont_exist] not found
为什么第二个版本不起作用,我在模板中使用data.items?
Why isn't the second version working, where I use data.items in my template?
这是 Django中的已知问题:您无法遍历模板中的defaultdict
.文档建议处理此问题的最佳方法是:将您的defaultdict
转换为dict
,然后再传递给模板:
This is a known issue in Django: you cannot iterate over a defaultdict
in a template. The docs suggest that the best way to handle this is to convert your defaultdict
to a dict
before passing it to the template:
context['data'] = dict(assertion_dict)
顺便说一句,它不起作用的原因是,当您在模板中调用{{ data.items }}
时,Django将首先尝试找到data['items']
,然后是data.items
. defaultdict
将为前者返回默认值,因此Django将不会尝试后者,而您最终将尝试遍历默认值而不是dict.
The reason it doesn't work, by the way, is that when you call {{ data.items }}
in your template, Django will first attempt to find data['items']
, and then data.items
. The defaultdict
will return a default value for the former, so Django will not attempt the latter, and you end up trying to loop over the default value instead of the dict.