Подтвердить что ты не робот

Как удалить дублированные элементы в массиве на Twig

Как удалить дублированные элементы в массиве на Twig?

У меня есть значение массива в ветке, например.

{{ set array = ["testA","testB","testA","testC","testB"]  }}

Я хочу удалить дублированные элементы и использовать только testA, testB, testC

{% for name in array%}

 //skip the duplicate items and use only testA,testB,testC

{% endfor %}

Как я могу это сделать?

4b9b3361

Ответ 1

Twig - движок VIEW и не должен использоваться - в теории - для управления данными. Это (очень) хорошая практика для использования (предположительно) PHP для сбора данных, выполнения всех необходимых манипуляций, а затем передачи правильных данных в ваш вид.

Итак, вот как вы можете это сделать в чистом синтаксисе Twig:

{% set newArray = [] %}

{% for name in array %}
   {% if name not in newArray %}
     My name is {{name}}
   {% set newArray = newArray|merge([name]) %}
   {% endif %}


{% endfor %}

Ответ 2

В этом случае, как @Webberig сказал, что лучше подготовить свои данные до рендеринга представления. Но когда у вас есть более сложный процесс, и если это связано с представлением, вы можете создать расширение Twig, с расширением код будет выглядеть так:

MyTwigExtension.php для версий Twig 1.12 и выше:

/**
 * {@inheritdoc}
 */
public function getFunctions()
{
    return array(
        new \Twig_SimpleFunction('array_unset', array($this, 'arrayUnset'))
    );
}

Если вы используете версию Twig раньше 1.12, вместо этого используйте MyTwigExtension.php:

/**
 * {@inheritdoc}
 */
public function getFunctions()
{
    return array(
        'array_unset' => new \Twig_Function_Method($this, 'arrayUnset')
    );
}
/**
 * Delete a key of an array
 *
 * @param array  $array Source array
 * @param string $key   The key to remove
 *
 * @return array
 */
public function arrayUnset($array, $key)
{
    unset($array[$key]);

    return $array;
}

Twig:

{% set query = array_unset(query, 'array_key') %}

Ответ 3

Быстрый ответ (TL; DR)

  • Пользовательский фильтр Twig array_unique позволяет удалить дубликаты
  • Это может быть непосредственно перенесено из собственного PHP

Подробный ответ

Контекст

  • Twig 2.x(последняя версия от Wed 2017-02-08)
  • Альтернативный подход по сравнению с другими подходами, указанными в другом месте

Проблема

  • Сценарий:
  • DeloperSutasSugas хочет удалить массив
  • Встроенная функция array_unique PHP может выполнять работу

Example01

  • DeloperSutasSugas начинается с последовательно-индексированного массива
  • преобразуется из BEFORE в AFTER
{%- set mylist = ['alpha','alpha','bravo','charlie','alpha','alpha','delta','echo']  -%}

BEFORE: 
['alpha','alpha','bravo','charlie','alpha','alpha','delta','echo']

AFTER: 
['alpha','bravo','charlie','delta','echo']

Решение

Пользовательский фильтр
[...]
// {"define_filter_":"array_unique" ,"desc":"PHP array_unique function" },
$filter = new Twig_SimpleFilter('array_unique', function ( $vinp=Array() ) {
  $vout = ( $vinp );
  $vout = array_unique( $vout );
  $vout = array_values( $vout ); // PHP annoyance array reindex -- optional
  return $vout;
});
$twig->addFilter($filter);
//;;
[...]
Вывод
{%- set mylist = mylist|array_unique  -%}    

Ловушки

  • Требуется фильтр аддона (решение не работает с родным Twig)

См. также

Ответ 4

Для Symfony!

Сервис: app/config/service.yml

twig_array_unique_function:
    class: AppBundle\Twig\ArrayUniqueFunction
    tags:
        - { name: twig.function }

Класс: src/AppBundle/Twig/ArrayUniqueFunction.php

<?php

namespace AppBundle\Twig;

class ArrayUniqueFunction extends \Twig_Extension
{
    public function getFilters()
    {
        return [new \Twig_SimpleFilter('array_unique', 'array_unique')];
    }

    public function getFunctions()
    {
        return [new \Twig_SimpleFunction('array_unique', 'array_unique')];
    }
}

Спасибо: https://github.com/getgrav/grav/blob/develop/system/src/Grav/Common/Twig/TwigExtension.php

Ответ 5

{% set keeper = {} %}
{% set throwaway = [] %}
{% for thing in yourSet.all() %}

  {% if thing.id not in throwaway %}
    {% set throwaway = throwaway|merge([thing.id]) %}
    {% set keeper = keeper|merge([{ slug: thing.slug, title: thing.title}]) %}
  {% endif %}

{% endfor %}

Модификация по принятому ответу выше. Мне нужно было удалить дубликаты из набора и получить объект только слаг и заголовок.

Ответ 6

Вы можете сделать это в одну строку, начиная с Twig 1.41 и 2.10:

{% set unique = array|reduce(
    (unique, item) => item in unique ? unique : unique|merge([item]), []
) %}

В вашем примере:

{% for name in array|reduce((unique, item) => item in unique ? unique : unique|merge([item]), []) %}
     My name is {{name}}
{% endfor %}