Разрушающее присваивание в php для объектов / ассоциативных массивов

В CoffeeScript, Clojure, ES6 и многих других языках мы деструктурируем объекты / карты / и т. Д. Примерно так:

obj = {keyA: 'Hello from A', keyB: 'Hello from B'}
{keyA, keyB} = obj

Я нашел list функция в PHP, который позволяет вам деструктурировать массивы следующим образом:

$info = array('coffee', 'brown', 'caffeine');
list($drink, $color, $power) = $info;

Есть ли способ деструктурировать объекты или ассоциативные массивы в PHP? Если не в ядре libs, может быть, кто-то написал какую-нибудь умную вспомогательную функцию?

15

Решение

Для PHP 7.0 и ниже это выходит за рамки функциональности list, Документы утверждают:

list работает только с числовыми массивами и предполагает, что числовые индексы начинаются с 0.

Одной из вещей, которая может удовлетворить ваши цели, будет extract() функция, которая импортирует переменные из массива в текущую таблицу символов. Хотя с list Вы можете определить имена переменных в явном виде, extract() не дает тебе этой свободы.

Извлечение ассоциативного массива

С extract Вы могли бы сделать что-то подобное:

<?php

$info = [ 'drink' => 'coffee', 'color' => 'brown', 'power' => 'caffeine' ];
extract($info);

var_dump($drink); // string(6) "coffee"var_dump($color); // string(5) "brown"var_dump($power); // string(8) "caffeine"

Извлечение объекта

Извлечение объекта работает практически так же. поскольку extract только принимает массив в качестве аргумента, нам нужно получить свойства объектов в виде массива. get_object_vars делает это для вас. Возвращает ассоциативный массив со всеми общественности свойства в качестве ключа и их значения в качестве значения.

<?php

class User {

public $name = 'Thomas';

}

$user = new User();
extract( get_object_vars($user) );

var_dump($name); // string(6) "Thomas"

Ловушки

extract() это не то же самое, что list поскольку он не позволяет явно определять имена переменных, которые экспортируются в таблицу символов. Имена переменных по умолчанию соответствуют ключам массива.

  • list это языковая конструкция в то время как extract() это функция
  • Может случиться так, что вы непреднамеренно перезаписываете переменные, которые вы определили заранее
  • Ключи вашего массива могут быть неверными в качестве имен переменных

С $flags параметр, который вы можете передать в качестве второго аргумента extract() Вы можете повлиять на поведение в случае столкновения или недопустимых переменных. Но все же важно знать, как extract() работает и использовать его с cauton.

Редактировать: Начиная с PHP 7.1 это возможно:

Теперь вы можете указать ключи в list () или в его новом сокращенном синтаксисе []. Это позволяет деструктурировать массивы с нецелыми или непоследовательными ключами. — http://php.net/manual/en/migration71.new-features.php#migration71.new-features.symmetric-array-destructuring

Сокращенный синтаксис массива ([]) теперь может использоваться для деструктурирования массивов для назначений (в том числе внутри foreach), в качестве альтернативы существующему синтаксису list (), который все еще поддерживается. — http://php.net/manual/en/migration71.new-features.php#migration71.new-features.support-for-keys-in-list

Например это:

$test_arr = ['a' => 1, 'b' => 2];
list('a' => $a, 'b' => $b) = $test_arr;
var_dump($a);
var_dump($b);

Будет выводить следующее, начиная с 7.1.0

int(1)
int(2)
23

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

Переменные являются одним из способов сделать это. foreach держит вас в области видимости, так что вы можете явно определить свои переменные из массива следующим образом:

$args = ['a' => 1, 'b' => 2, 'c' => 3];
foreach (['a', 'c'] as $v) $$v = $args[$v];
// $a is 1, $b is undefined, $c is 3

Это действительно не красиво, и, к счастью, это было решено в 7.1 https://wiki.php.net/rfc/short_list_syntax . Это позволит вам сказать ['a' => $a, 'c' => $c] = $args; в приведенном выше примере.

Так как 7.1 включает в себя способ использовать другое имя для вашей переменной, чем ключ массива Assoc, я упомяну, что это довольно просто, используя мой подход и здесь.

foreach (['a' => 'eh', 'b' => 'bee'] as $k => v) $$v = $args[$k];
// $eh is 1, $bee is 2
0

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