Переведите одну строку Perl в переполнение стека

Я переводю файл с Perl на PHP, но мне нужна помощь с этой строкой:
@stuff_unique = grep !$list{$_}++, @stuff;,
я знаю stuff_unique а также stuff являются массивами.

4

Решение

Это распространенная идиома Perl, описанная в perlfaq4

С этой конструкцией @stuff_unique в конечном итоге список предметов, которые были замечены по крайней мере один раз в @stuff; другими словами, в нем остаются только уникальные значения, в том смысле, что повторов не будет. Вот как это работает:

Хэш в Perl похож на ассоциативный массив с уникальными ключами. %list такой хэш $list{something} является элементом в этом хэше с именем «что-то». Его ценность может быть любой, что вы вкладываете в нее.

grep перебирает элементы в @stuff, Для каждого элемента в stuffэтот элемент используется в качестве хеш-ключа в %list хэш. ++ увеличивает значение для этого соответствующего хеш-элемента. Так что если @stuff содержит «1, 2, 1», тогда на первой итерации будет создан хеш-элемент с именем «1». Он не имеет значения, что переводится как логическое значение false. ! впереди меняет булево значение. Таким образом, на этой первой итерации ложное значение для хеш-элемента ‘1’ оценивается как истинное, поэтому этот элемент проходит через @stuff_unique, Наконец, выполняется постинкремент, поэтому значение, хранящееся в 1 элемент хеша увеличивается до 1.

На втором элементе, 2 также еще не был замечен, поэтому он проходит, и его соответствующий хэш-элемент также увеличивается до 1.

На третьей итерации снова появляется «1». $list{1} уже равен 1, который является истинным значением. ! истинно ложно; так что этот не проходит через @stuff_unique,

Один за другим элементы в @stuff будет проверен таким образом; обнаружение, если они были замечены ранее, и если они не видели, они проходят через @stuff_unique,

PHP предоставляет функцию под названием array_unique, который должен сделать то же самое для вас. Это будет использовано так:

$stuff_unique = array_unique($stuff);

К счастью для Perl, это линейная операция. К сожалению для людей PHP, это реализовано внутри, сортируя входной массив, а затем перебирая его, пропуская дубликаты по пути. Это означает, что это O(n + n log n) операция (упрощенная до O(n log n)), то есть его реализация не может масштабироваться так же, как обычная идиома Perl.

7

Другие решения

Радость использования php замыканий,

<?php

$stuff = array(1,1,2,2,2,3,3,3);

$list = array();
$stuff_unique = array_filter($stuff, function($_) use (&$list) {
return !$list[$_]++;
});

print_r(array_values($stuff_unique));

или же

<?php

$stuff = array(1,1,2,2,2,3,3,3);
$stuff_unique = array_keys(array_flip($stuff));

print_r($stuff_unique);

или же

$stuff_unique = array_values(array_unique($stuff));
2

По вопросам рекламы [email protected]