Python Django模板如何使用变量查找字典值
在Django模板中查找字典值的常规方法是Python Django模板如何使用变量查找字典值,python,django,templates,dictionary,Python,Django,Templates,Dictionary,在Django模板中查找字典值的常规方法是{{mydict.key1},{{mydict.key2}。如果键是一个循环变量怎么办?即: mydict = {"key1":"value1", "key2":"value2"} mydict.item.NAME失败。如何修复此问题?默认情况下,您不能。点是属性查找/键查找/切片的分隔符/触发器 点在模板渲染中具有特殊意义。变量中的点 名称表示查找。具体来说,当模板系统 遇到变量名中的点,它会尝试以下查找, 按此顺序: 查字典。示例:foo[“ba
{{mydict.key1}
,{{mydict.key2}
。如果键是一个循环变量怎么办?即:
mydict = {"key1":"value1", "key2":"value2"}
mydict.item.NAME
失败。如何修复此问题?默认情况下,您不能。点是属性查找/键查找/切片的分隔符/触发器
点在模板渲染中具有特殊意义。变量中的点
名称表示查找。具体来说,当模板系统
遇到变量名中的点,它会尝试以下查找,
按此顺序:
- 查字典。示例:foo[“bar”]
- 属性查找。示例:foo.bar
- 列表索引查找。示例:foo[bar]
.get
这样,如果键不存在,它将返回none。如果使用字典[key]
它将引发键错误
)
用法:
from django.template.defaulttags import register
...
@register.filter
def get_item(dictionary, key):
return dictionary.get(key)
从循环中的字典中获取键和值:
{{ mydict|get_item:item.NAME }}
我发现这更容易阅读,并且避免了特殊编码的需要。无论如何,我通常需要循环中的键和值。我也遇到过类似的情况。然而,我使用了不同的解决方案 在我的模型中,我创建了一个进行字典查找的属性。然后在模板中使用属性 在我的模型中:-
{% for key, value in mydict.items %}
{{ value }}
{% endfor %}
在我的模板中:-
@property
def state_(self):
""" Return the text of the state rather than an integer """
return self.STATE[self.state]
对我来说,在我的应用程序中创建一个名为
template\u filters.py
的python文件,并使用以下内容完成了任务
The state is: {{ item.state_ }}
用法就像库莱布伦所说的:
# coding=utf-8
from django.template.base import Library
register = Library()
@register.filter
def get_item(dictionary, key):
return dictionary.get(key)
环境:django 2.1.7
视图:
{{ mydict|get_item:item.NAME }}
模板:
dict_objs[query_obj.id] = {'obj': query_obj, 'tag': str_tag}
return render(request, 'obj.html', {'dict_objs': dict_objs})
{%for obj_id,dict_objs.items%中的dict_obj}
{{dict_obj.obj.obj_name}
{{obj_id}}
{{forloop.counter}}
{{dict_obj.obj.update_timestamp}日期:“Y-m-dh:i:s”}
因为我不能发表评论,所以让我以回答的形式来回答:要在或的基础上构建,传递到函数中的字典是字符串形式的,因此可能需要先使用将字符串转换为字典,如中所示 通过此编辑,代码应如下所示:
{% for obj_id,dict_obj in dict_objs.items %}
<td>{{ dict_obj.obj.obj_name }}</td>
<td style="display:none">{{ obj_id }}</td>
<td>{{ forloop.counter }}</td>
<td>{{ dict_obj.obj.update_timestamp|date:"Y-m-d H:i:s"}}</td>
#自定义模板标记的代码
@register.filter(name='lookup')
def查找(值,参数):
value\u dict=ast.literal\u eval(值)
返回值\u dict.get(arg)
{{mydict |查找:item.name}
环境:Django 2.2
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [os.path.join(BASE_DIR, 'templates')],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
'libraries':{
'template_filters': 'portfoliomgr.template_filters',
}
},
},
]
,供将来发现此功能的用户使用。为什么默认情况下不内置此功能-(我想@Jeff在Jinja2中的意思是{{mydict[key]}}过滤器是否在views.py、一些额外的filters.py或什么文件中?他没有要求枚举dict(如您所示)-他要求获得给定变量键的dict值。您的建议没有提供解决方案。这是一个解决方案(只是效率很低)因为您可以枚举dict的项,然后与列表中的键进行匹配。请注意,如果您尝试访问的词典中包含另一个词典,则此操作不起作用。如果您的值是dict,则可以包含另一个for循环来处理它们的键和值,但其复杂性可能会将您带向它正如@culebron的回答中所述,使用自定义过滤器是值得的。为什么
register=Library()
?它做什么?如果你想让所有模板都知道你的新过滤器,那么你必须在django.template.base.Library
class.byregister=Library()下注册它
我们实例化该类,并在其中使用过滤器函数注释器来满足我们的需要。模板代码{{dict_obj.obj.obj_name}
在本例中相当于Python代码dict_obj[“obj”][“obj_name”]
,然而,问题是关于dict_obj[obj][obj_name]的等价物
。如何在模板中使用答案?我仍然会使用返回值。get(arg)
,因为如果键不存在,这不会引发KeyError异常。是否可以分配返回的值({{mydict | lookup:item.name})到variable@Jibin我不知道你的问题是什么意思。也许我的代码让人困惑;从那时起,我已经纠正了它并添加了注释。
{% for obj_id,dict_obj in dict_objs.items %}
<td>{{ dict_obj.obj.obj_name }}</td>
<td style="display:none">{{ obj_id }}</td>
<td>{{ forloop.counter }}</td>
<td>{{ dict_obj.obj.update_timestamp|date:"Y-m-d H:i:s"}}</td>
# code for custom template tag
@register.filter(name='lookup')
def lookup(value, arg):
value_dict = ast.literal_eval(value)
return value_dict.get(arg)
<!--template tag (in the template)-->
{{ mydict|lookup:item.name }}
from django.template.defaulttags import register
@register.filter(name='lookup')
def lookup(value, arg):
return value.get(arg)
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [os.path.join(BASE_DIR, 'templates')],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
'libraries':{
'template_filters': 'portfoliomgr.template_filters',
}
},
},
]
{% load template_filters %}