Cài đặt phần tử của mảng từ Twig


125

Làm cách nào tôi có thể đặt thành viên của một mảng đã có từ Twig?

Tôi đã thử làm theo cách tiếp theo:

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

nhưng tôi đã nhận được lỗi sau:

Mã thông báo bất ngờ "chấm câu" của giá trị "[" ("kết thúc khối lệnh" dự kiến) trong ...

Câu trả lời:


210

Không có cách nào hay để làm điều này trong Twig. Tuy nhiên, có thể bằng cách sử dụng bộ lọc hợp nhất:

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

"." - câu lệnh giống như "[]" vì vậy đó không phải là giải pháp
falinsky

@falinsky Bạn nói đúng. .[]rất giống nhau trong Twig và tôi đã sai. Tôi nhìn nó và chỉnh sửa câu trả lời của tôi.
Paul

17
Tôi đang tìm cách để xác định khóa biến động thay thế 'element'. Tôi tìm thấy câu trả lời của @ LivaX bên dưới. Vì vậy, nó sẽ được {% set arr = arr|merge({(key): 'value'}) %}.
Sithu

Điều này thật ngớ ngẩn. Tại sao twig không cho phép khả năng đặt giá trị mảng?
Matt Cavanagh

1
@MattCavanagh vì các tệp xem (như Twig) không được cho là chứa logic nghiệp vụ, điều này cuối cùng sẽ được xử lý trong mô hình. Khung cảnh thực sự được cho là chỉ đơn giản là hiển thị những gì ở đó. Vấn đề mặc dù trong trường hợp của tôi và tại sao tôi cũng đồng ý với bạn, đó là tôi tạo các macro twig để hiển thị các đối tượng UI, vd. {{ UI.button({'type':'submit'}) }}và tất cả các macro này sử dụng | merge để đặt tham số mặc định, do đó cần có logic cho việc này ...
Prof83

79

Tôi gặp vấn đề này nhưng đã cố gắng tạo các chỉ mục nguyên thay vì chỉ mục liên kết như 'phần tử'.

Bạn cũng cần bảo vệ khóa chỉ mục của mình bằng ()cách sử dụng bộ lọc hợp nhất:

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

Bây giờ bạn có thể thêm khóa chỉ mục tùy chỉnh như ('element'~loop.index0)


Đó là giải pháp thực tế khi bạn cố gắng chèn các phím động, cảm ơn LivaX!
nicolallias

19

Nếu khởi tạo chỉ cần:

{% set items = { 'apple': 'fruit', 'orange': 'fruit', 'peugeot': 'unknown' } %}

8
Đây không phải là câu hỏi.
redreinard

2

Tôi đã thử câu trả lời của @LivaX nhưng nó không hoạt động, hợp nhất một mảng trong đó các khóa là số không hoạt động ( https://github.com/twigphp/Twig/issues/789 ).

Điều đó sẽ chỉ hoạt động khi các phím là chuỗi

Những gì tôi đã làm là tạo lại một bảng khác ( temp) từ bảng ban đầu ( t) và tạo các khóa thành một chuỗi, ví dụ:

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

t các phím: 0, 1, 2 ..

temp các phím: 0_, 1_, 2_ ....


Vấn đề tương tự, không có giải pháp cho đến nay.
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'%}

Cảm ơn chủ đề này - Tôi cũng có thể tạo một mảng với (loop.index0) và gửi đến twig.


1

Tôi thấy vấn đề này rất khó chịu và giải pháp của tôi có lẽ là chính thống và không phù hợp với triết lý Twig, nhưng tôi đã phát triển như sau:

$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);

có thể được sử dụng như sau:

{% set Array = set_element (mảng, 'phần tử', 'value')%}


1

Chỉ cần sử dụng như thế này {% set arr={'key':'value'} %}(không có khoảng trống sau :), nó hoạt động tốt.

Nhưng khi tôi sử dụng nó trong một vòng lặp for, để biến nó thành một mảng, nó không hoạt động bên ngoài phạm vi 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
Nếu bạn muốn sử dụng biến ngoài vòng lặp for, bạn cần xác định nó bên ngoài vòng lặp for, xem tại đây: twig.sensiolabs.org/doc/tags/set.html
user2019515

5
Đây là tất cả các loại sai. Không gian sau dấu hai chấm không quan trọng. Bạn đang tạo các mảng mới, không đặt một phần tử trong mảng đó là câu hỏi. Bạn không thể xuất ra một mảng như {{mảng}}, điều đó sẽ gây ra lỗi. Câu trả lời này đầy thất bại và không liên quan đến câu hỏi được hỏi.
redreinard

3
Tôi không hiểu tại sao điều này có upvote, như đã nêu ở trên, hầu hết mọi thứ đều không chính xác trong "câu trả lời" này ...
MariusJP

0

Tôi đã có một mảng đa chiều. Giải pháp duy nhất tôi có thể tìm ra là tạo một mảng tạm thời mới và cập nhật / thêm thông tin, tiếp tục được chuyển sang một chức năng twig khác.


0

Tôi đã có vấn đề này một thời gian trước đây. Hãy tưởng tượng bạn có một mảng như thế này:

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'
}

Vì vậy, bạn muốn hiển thị dữ liệu này thành hai hàng, nhưng xóa mật khẩu khỏi danh sách đó. Để kết thúc này, việc chia thành 2 mảng sẽ dễ dàng với slicebộ lọc. Tuy nhiên, chúng tôi phải xóa mật khẩu. Vì lý do đó, tôi đang sử dụng đoạn trích này. Ý tưởng là đặt tất cả các phần tử nhỏ hơn datakích thước phần tử chia cho 2. Để tính toán điều này, chúng tôi sử dụng bộ lọc length. Bây giờ để có được chỉ số của các yếu tố hiện tại chúng tôi sử dụng loop.index. Và cuối cùng chúng tôi * đẩy một yếu tố kết hợp trong mảng bên trái hoặc bên phải. Một mảng kết hợp có hai thành phần keyvalue. Để tham chiếu một khóa mảng trong twit chúng ta toán tử ()và chúng ta sử dụng mergebộ lọc để đẩy vào mảng như được hiển thị ở đây{% set left_list = left_list|merge({ (key): value }) %}

Đây là giải pháp hoàn chỉnh.

{% 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

Bạn cũng có thể sử dụng cú pháp sau:

{% set myArray = myArray + myArray2 %}
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.