In PHP 7.1 we can do the following:
<?php
[$a, $b, $c] = ['a', 'b', 'c'];
?>
Before, we had to do:
<?php
list($a, $b, $c) = ['a', 'b', 'c'];
?>
(PHP 4, PHP 5, PHP 7, PHP 8)
list — Asigna variables como si fueran un array
Al igual que array(), list() no es una
función real, sino un elemento del lenguaje, que permite reunir
las variables varname
, ...
en forma de array, para asignarlas en una sola línea.
Las cadenas de caracteres no pueden ser desestructuradas y las expresiones
list() no pueden estar completamente vacías.
Nota:
Anterior a PHP 7.1.0, list() funciona únicamente en un array de índice numérico y asume que el índice numérico comienza en 0.
A partir de PHP 7.1.0, list() puede también contener claves explícitas, permitiendo así la desestructuración de arrays con claves no enteras o no secuenciales. Para más detalles sobre la desestructuración de arrays, ver la sección sobre la desestructuración de arrays.
var
Una variable.
vars
Variables adicionales.
Devuelve el array asignado.
Versión | Descripción |
---|---|
7.3.0 | El soporte para la asignación por referencia en la desestructuración de array ha sido añadido. |
7.1.0 | Es ahora posible especificar las claves en la list(). Esto permite desestructurar arrays con claves no enteras o no secuenciales. |
Ejemplo #1 Ejemplo con list()
<?php
$info = array('coffee', 'brown', 'caffeine');
// Lista todas las variables
list($drink, $color, $power) = $info;
echo "$drink is $color and $power makes it special.\n";
// Lista algunas variables
list($drink, , $power) = $info;
echo "$drink has $power.\n";
// O bien, usemos solo el tercero
list( , , $power) = $info;
echo "I need $power!\n";
// list() no funciona con cadenas de caracteres
list($bar) = "abcde";
var_dump($bar); // NULL
?>
Ejemplo #2 Ejemplo de uso de list()
<?php
$result = $pdo->query("SELECT id, name FROM employees");
while (list($id, $name) = $result->fetch(PDO::FETCH_NUM)) {
echo "id: $id, name: $name\n";
}
?>
Ejemplo #3 Uso de un sub-list()
<?php
list($a, list($b, $c)) = array(1, array(2, 3));
var_dump($a, $b, $c);
?>
int(1) int(2) int(3)
Ejemplo #4 list() y el orden de definición de los índices
El orden en el que los índices de un array a tratar por list() son definidos es irrelevante.
<?php
$foo = array(2 => 'a', 'foo' => 'b', 0 => 'c');
$foo[1] = 'd';
list($x, $y, $z) = $foo;
var_dump($foo, $x, $y, $z);
Dada la siguiente salida (note el orden de los elementos comparados y en qué orden fueron escritos en la sintaxis de la list()) :
array(4) { [2]=> string(1) "a" ["foo"]=> string(1) "b" [0]=> string(1) "c" [1]=> string(1) "d" } string(1) "c" string(1) "d" string(1) "a"
Ejemplo #5 list() con claves
A partir de PHP 7.1.0 list() puede ahora contener también claves explícitas, que pueden ser dadas como expresiones arbitrarias. La mezcla de claves int y string está permitida; Sin embargo, los elementos con y sin claves no pueden ser mezclados.
<?php
$data = [
["id" => 1, "name" => 'Tom'],
["id" => 2, "name" => 'Fred'],
];
foreach ($data as ["id" => $id, "name" => $name]) {
echo "id: $id, name: $name\n";
}
echo PHP_EOL;
list(1 => $second, 3 => $fourth) = [1, 2, 3, 4];
echo "$second, $fourth\n";
El resultado del ejemplo sería:
id: 1, name: Tom id: 2, name: Fred 2, 4
In PHP 7.1 we can do the following:
<?php
[$a, $b, $c] = ['a', 'b', 'c'];
?>
Before, we had to do:
<?php
list($a, $b, $c) = ['a', 'b', 'c'];
?>
Since PHP 7.1, keys can be specified
exemple :
<?php
$array = ['locality' => 'Tunis', 'postal_code' => '1110'];
list('postal_code' => $zipCode, 'locality' => $locality) = $array;
print $zipCode; // will output 1110
print $locality; // will output Tunis
?>
The example showing that:
$info = array('kawa', 'brązowa', 'kofeina');
list($a[0], $a[1], $a[2]) = $info;
var_dump($a);
outputs:
array(3) {
[2]=>
string(8) "kofeina"
[1]=>
string(5) "brązowa"
[0]=>
string(6) "kawa"
}
One thing to note here is that if you define the array earlier, e.g.:
$a = [0, 0, 0];
the indexes will be kept in the correct order:
array(3) {
[0]=>
string(4) "kawa"
[1]=>
string(8) "brązowa"
[2]=>
string(7) "kofeina"
}
Thought that it was worth mentioning.
As noted, list() will give an error if the input array is too short. This can be avoided by array_merge()'ing in some default values. For example:
<?php
$parameter = 'name';
list( $a, $b ) = array_merge( explode( '=', $parameter ), array( true ) );
?>
However, you will have to array_merge with an array long enough to ensure there are enough elements (if $parameter is empty, the code above would still error).
An alternate approach would be to use array_pad on the array to ensure its length (if all the defaults you need to add are the same).
<?php
$parameter = 'bob-12345';
list( $name, $id, $fav_color, $age ) = array_pad( explode( '-', $parameter ), 4, '' );
var_dump($name, $id, $fav_color, $age);
/* outputs
string(3) "bob"
string(5) "12345"
string(0) ""
string(0) ""
*/
?>
The example states the following:
<?php
// list() doesn't work with strings
list($bar) = "abcde";
var_dump($bar);
// output: NULL
?>
If the string is in a variable however, it seems using list() will treat the string as an array:
<?php
$string = "abcde";
list($foo) = $string;
var_dump($foo);
// output: string(1) "a"
?>
<?php
/**
* It seems you can skip listed values.
* Here's an example to show what I mean.
*
* FYI works just as well with PHP 7.1 shorthand list syntax.
* Tested against PHP 5.6.30, 7.1.5
*/
$a = [ 1, 2, 3, 4 ];
// this is quite normal use case for list
echo "Unpack all values\n";
list($v1, $v2, $v3, $v4) = $a;
echo "$v1, $v2, $v3, $v4\n";
unset($v1, $v2, $v3, $v4);
// this is what I mean:
echo "Skip middle\n";
list($v1, , , $v4) = $a;
echo "$v1, $v2, $v3, $v4\n";
unset($v1, $v2, $v3, $v4);
echo "Skip beginning\n";
list( , , $v3, $v4) = $a;
echo "$v1, $v2, $v3, $v4\n";
unset($v1, $v2, $v3, $v4);
echo "Skip end\n";
list($v1, $v2, , ) = $a;
echo "$v1, $v2, $v3, $v4\n";
unset($v1, $v2, $v3, $v4);
echo "Leave middle\n";
list( , $v2, $v3, ) = $a;
echo "$v1, $v2, $v3, $v4\n";
unset($v1, $v2, $v3, $v4);
It can be convenient to specify a default value in case an element is missing in the list. You can use operator + for this:
<?php
$someArray = ['color' => 'orange'];
['color' => $color, 'size' => $size] = $someArray + ['color' => null, 'size' => null];
?>
This will avoid the warning `Undefined array key "size"` you would encounter otherwise.
list() can be used with foreach
<?php
$array = [[1, 2], [3, 4], [5, 6]];
foreach($array as list($odd, $even)){
echo "$odd is odd; $even is even", PHP_EOL;
}
?>
The output:
===
1 is odd; 2 is even
3 is odd; 4 is even
5 is odd; 6 is even
The list construct seems to look for a sequential list of indexes rather taking elements in sequence. What that obscure statement means is that if you unset an element, list will not simply jump to the next element and assign that to the variable but will treat the missing element as a null or empty variable:
$test = array("a","b","c","d");
unset($test[1]);
list($a,$b,$c)=$test;
print "\$a='$a' \$b='$b' \$c='$c'<BR>";
results in:
$a='a' $b='' $c='c'
not:
$a='a' $b='c' $c='d'
Don't miss simple array pattern matching since php 7
<?php
[$a] = ['hello!'];
var_dump($a); // 'hello!'
$arr = [4 => 50];
[4 => $fifty] = $arr;
var_dump($fifty); // 50
$multidimensionalArray = [['id' => 15, 'email' => 'diyor024@gmail.com']];
[['id' => $id, 'email' => $email]] = $multidimensionalArray;
var_dump($id, $email); // 15 diyor024@gmail.com
?>
Setting it like <?php list($var1,$varN) = null ?> does _not_ raise an E_NOTICE (or other error) and afaics effectively equals an https://php.net/function.unset of $var1,$varN.
I note this as contrasting with the fact that PHP triggers an E_NOTICE about "Undefined offset" "if there aren't enough array elements to fill the list()", as attow documented for https://php.net/control-structures.foreach#control-structures.foreach.list and here only noted in https://php.net/function.list#122951 by Mardaneus.
For completeness, a bash(1) (v5.0 or 4.3 on macos10.13) cli test producing the same result for all my PHP-versions (installed via macports.org) follows. It's also tested with php7.3 using bash5.0 on Debian10:
bash --noprofile --norc -c 'for php in php{{53..56},{70..73}};do for literal in "array()" null;do echo -n $php …=$literal:&&$php -n -d error_reporting=E_ALL -r "var_dump(list(\$var)=$literal);";done;done'
# Above produces the same result pairs per version from:
php53 …=array():
Notice: Undefined offset: 0 in Command line code on line 1
array(0) {
}
# ... to:
php73 …=null:NULL
The list() definition won't throw an error if your array is longer then defined list.
<?php
list($a, $b, $c) = array("a", "b", "c", "d");
var_dump($a); // a
var_dump($b); // b
var_dump($c); // c
?>
For PHP 7.1 on, the documentation states that integer and string keys can be mixed, but that elements with and without keys cannot. Here is an example, using data from getimagesize() with mixed keys:
<?php
$data=[
0=> 160,
1 => 120,
2 => 2,
3 => 'width="160" height="120"',
'mime' => 'image/jpeg'
];
list(0=>$width,1=>$height,2=>$type,3=>$dimensions,'mime'=>$mime)=$data;
?>
Here, the numeric keys also need to be specified, as if the whole array is treated as an associative array.
As noted elsewhere, the list() operator can be written in array format:
<?php
[0=>$width,1=>$height,2=>$type,3=>$dimensions,'mime'=>$mime]=$data;
?>
This is something I haven't seen in documentation.
Since PHP 7.1, you can use short-hand list unpacking using square brackets, just like short-hand array declaration:
<?php
$foo = ['a', 'b', 'c'];
// short-hand array definition
[$a, $b, $c] = $foo;
echo $a; // displays "a"
// it's same like:
list($x, $y, $z) = $foo;
echo $x; // displays "a"
?>
list($a, $b, $c) = ["blue", "money", 32];
shortcut:
[$a, $b, $c] = ["blue", "money", 32];
From PHP Version 7.1 you can specify keys in list(), or its new shorthand [] syntax. This enables destructuring of arrays with non-integer or non-sequential keys.
<?php
$data = [
["id" => 1, "name" => 'Tom'],
["id" => 2, "name" => 'Fred'],
];
// list() style
list("id" => $id1, "name" => $name1) = $data[0];
// [] style
["id" => $id1, "name" => $name1] = $data[0];
// list() style
foreach ($data as list("id" => $id, "name" => $name)) {
// logic here with $id and $name
}
// [] style
foreach ($data as ["id" => $id, "name" => $name]) {
// logic here with $id and $name
}
Since 7.1.0, you can use an array directly without list():
<?php
[$test, $test2] = explode(",", "hello, world");
echo $test . $test2; // hello, world
?>
a simple example of use to swap two variables :
$a = 'hello';
$b = 'world';
list($a, $b) = [$b, $a];
echo $a . ' ' . $b; //display "world hello"
another example :
function getPosition($x, $y, $z)
{
// ... some operations like $x++...
return [$x, $y, $z];
}
list($x, $y, $z) = getPosition($x ,$y, $z);
Since PHP 7.1 the [] may now be used as an alternative to the existing list() syntax:
<?php
[$number, $message] = explode('|', '123|Hello World!');
?>
If you want use the undefined behaviour as you might expect it e.g. if you want:
$b = ['a','b']; list($a, $b) = $b;
to result in $a=='a' and $b=='b', then you can just cast $b to an array (even although it already is) to create a copy. e.g.
$b = ['a','b']; list($a, $b) = (array)$b;
and get the expected results.
... and it also supports pushing items onto arrays.
I couldn't find any official documentation on this behavior, but it appears that you can "push" elements onto arrays directly using array destructuring assignments.
<?php
$users = [
[1, 'Alice', 'alice@example.com', 'secret123'],
[2, 'Bob', 'bob@example.com', 'pass456'],
[3, 'Charlie', 'charlie@example.com', 'hunter678'],
];
$ids = [];
$names = [];
$emails = [];
$passwords = [];
foreach ($users as $user) {
[$ids[], $names[], $emails[], $passwords[]] = $user;
}
?>
For well-documented alternatives, consider using array_column(), which does quite the same:
<?php
$ids = array_column($users, 0);
$names = array_column($users, 1);
$emails = array_column($users, 2);
$passwords = array_column($users, 3);
?>
Unless you specify keys when using list() it expects the array being fed into it to start at 0.
So having the following code will result in a notice level warning "Undefined offset: 0" and variables not filling as expected
<?php
list($c1, $c2, $c3) = array [1 =>'a', 2 => 'b', 3 => 'c'];
var_dump($c1); // NULL
var_dump($c2); // string(1) "a"
var_dump($c3); // string(1) "b"
?>
UNDOCUMENTED BEHAVIOR:
list($a,$b,$c) = null;
in fact works like:
$a = null; $b = null; $c = null;
...So correspondingly:
list($rows[]) = null;
Will increment count($rows), just as if you had executed $rows[] = null;
Watch out for this (for example) when retrieving entire tables from a database, e.g.
while (list($rows[]) = $mysqlresult->fetch_row());
This will leave an extra 'null' entry as the last element of $rows.
Easy way to get actual date and time values in variables.
list($day,$month,$year,$hour,$minute,$second) = explode('-',date('d-m-Y-G-i-s'));
echo "$day-$month-$year $hour".":".$minute.":".$second;