从Twig设置数组的元素


125

如何设置来自Twig的现有数组的成员?

我试图用下面的方法做:

{% set arr['element'] = 'value' %}

但出现以下错误:

...中的值“ [”(预期为“语句块结尾”)出现意外的标记“标点”

Answers:


210

在Twig中没有很好的方法可以做到这一点。但是,可以使用合并过滤器:

{% set arr = arr|merge({'element': 'value'}) %}

“。”声明与“ []”相同,因此不是解决方案
falinsky

@falinsky你是对的。.[]Twig非常相似,我错了。我查了一下并编辑了答案。
保罗

17
我一直在寻找一种方法来定义动态变量键来代替'element'。我在下面找到了@LivaX的答案。因此,它将是{% set arr = arr|merge({(key): 'value'}) %}
锡胡

真傻 为什么Twig不允许设置数组值?
马特·卡瓦纳

1
@MattCavanagh因为视图文件(例如Twig)不应包含业务逻辑,所以最终应在模型中处理。视图实际上应该只是渲染其中的内容。但是,就我而言,以及为什么我也同意您的问题是,我创建了树枝宏来渲染UI对象。{{ UI.button({'type':'submit'}) }}并且所有这些宏都使用| merge来设置默认参数,因此对此存在逻辑上的需要……
Prof83,2016年

79

我遇到了这个问题,但是试图创建整数索引而不是像“元素”这样的关联索引。

您还需要()使用合并过滤器来保护索引键:

{% set arr = arr|merge({ (loop.index0): 'value'}) %} 

您现在可以添加自定义索引键,例如 ('element'~loop.index0)


当您尝试动态插入密钥时,这是实际的解决方案,谢谢LivaX!
nicolallias


2

我已经尝试了@LivaX的答案,但它不起作用,合并键为数字的数组将不起作用(https://github.com/twigphp/Twig/issues/789)。

仅当键为字符串时才有效

我所做的是temp从初始表(t)重新创建另一个表(),并使键成为字符串,例如:

{% for key , value in t%}
{% set temp= temp|merge({(key~'_'):value}) %}
{% endfor %}

t 键:0,1,2 ..

temp 键:0_,1_,2_ ....


同样的问题,到目前为止没有解决方案。
TyrionGraphiste

2
{% set links = {} %}

{# Use our array to wrap up our links. #}
{% for item in items %}
  {% set links = links|merge({ (loop.index0) : {'url': item.content['#url'].getUri(), 'text': item.content['#title']} }) %}
{% endfor %}

{%
set linkList = {
  'title': label,
  'links': links
}
%}

{% include '<to twig file>/link-list.twig'%}

感谢这个线程-我还能够使用(loop.index0)创建一个数组并将其发送到twig。


1

我发现这个问题很烦人,我的解决方案也许是正统的,不符合Twig哲学,但是我开发了以下内容:

$function = new Twig_Function('set_element', function ($data, $key, $value) {
    // Assign value to $data[$key]
    if (!is_array($data)) {
        return $data;
    }
    $data[$key] = $value;
    return $data;
});
$twig->addFunction($function);

可以如下使用:

{%set arr = set_element(arr,'element','value')%}


1

就像这样使用{% set arr={'key':'value'} %}(后面没有空格:),效果很好。

但是,当我在for循环内使用它以使其成为数组时,它在for范围外不起作用。

{% for group in user.groups %}
  {% set foo={'loop.index0':'group.id'} %}
  {% set title={'loop.index0':'group.title'} %}
  {{ title }} //it work 
{% else %}
  {% set foo={'0':'-1'} %}
  {% set title={'0':'未分组'} %}
{% endfor %}
{{ title }}  //it does not work, saying title is not defined

1
如果要在for循环外使用变量,则需要在for循环外定义变量,请参见此处:twig.sensiolabs.org/doc/tags/set.html
user2019515 2014年

5
这是各种各样的错误。冒号后面的空间无关紧要。您正在创建新的数组,而不是在问题中设置数组中的元素。您无法输出{{array}}之类的数组,否则会产生错误。这个答案充满了失败,与提出的问题无关。
redreinard 2015年

3
我不明白为什么会有这样的投票,如上所述,在此“答案”中几乎所有内容都不正确...
MariusJP

0

我有一个多维数组。我能找到的唯一解决方案是创建一个新的临时数组并更新/添加信息,该信息进一步传递给另一个树枝函数。


0

我前一段时间有这个问题。假设您有一个像这样的数组:

data = {
    'user': 'admin',
    'password': 'admin1234',
    'role': 'admin',
    'group': 'root',
    'profile': 'admin',
    'control': 'all',
    'level': 1,
    'session': '#DFSFASADASD02',
    'pre_oa': 'PRE-OA',
    'hepa_oa': 'HEPA-OA',
    'pre_ra': 'HEPA-RA',
    'hepa_ra': 'HEPA-RA',
    'deodor_ra': 'DEODOR-RA'
}

因此,您想在两行中显示此数据,但从该列表中删除密码。为此,使用slice过滤器很容易将其分成2个阵列。但是,我们必须删除密码。因此,我正在使用此代码段。我们的想法是将所有元素小于data元素大小除以2。要使用滤波器计算此元素length。现在,获取用户当前元素的索引loop.index。最后,我们将一个关联元素*推入左或右数组。关联数组具有key和的两个分量value。要在twit中引用数组键,我们需要操作符,()然后使用merge过滤器将数组推入数组,如下所示{% set left_list = left_list|merge({ (key): value }) %}

这是完整的解决方案。

{% set left_list = {} %}
{% set right_list = {} %}
{% set limit = data|length // 2 %}
{% for key, value in data|cast_to_array %}
{% if key != 'password' %}
{% if loop.index <= limit %}
{% set left_list = left_list|merge({ (key): value }) %}
{% else %}
{% set right_list = right_list|merge({ (key): value }) %}
{% endif %}
{% endif %}
{% endfor %}
{% for key, value in left_list %}
<p>
<label for="{{key}}">{{key}}</label>
<input type="text" name="{{key}}" id="{{key}}" value="{{value}}"
       class="text ui-widget-content ui-corner-all">
</p>
{% endfor %}

0

您还可以使用以下语法:

{% set myArray = myArray + myArray2 %}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.