@ 2016-05-07T23:45:22Z <?php
class Reference {
private static $DATA = [];
private $index = 0;
public function __construct($value) {
// cannot create a reference of a reference
if ($value instanceof self) {
$this->index = $value->index;
} else {
$this->index = count(self::$DATA);
self::$DATA[$this->index] = $value;
}
}
public function get() {
return self::$DATA[$this->index];
}
public function set($value) {
self::$DATA[$this->index] = $value;
}
}
$x = [1, 2, 3];
// foreach($x as &$ref) { ... }
/* $x[0] */
$x[0] = new Reference($x[0]); // Reference#0(index 0) = 1
$ref = clone $x[0]; // Reference#1(index 0)
$ref->set($ref->get() + 100); // set index 0 = 101
/* $x[1] */
$x[1] = new Reference($x[1]); // Reference#2(index 1) = 2
$ref = clone $x[1]; // Reference#3(index 1)
$x[0] = $x[0]->get(); // without $ref, $x[0] is the only reference to its value and demoted back to a value
$ref->set($ref->get() + 100); // set index 1 = 101
/* $x[2] */
$x[2] = new Reference($x[2]); // Reference#4(index 2) = 3
$ref = clone $x[2]; // Reference#5(index 2)
$x[1] = $x[1]->get(); // demoted
$ref->set($ref->get() + 100); // set index 2 = 103
// end foreach
/* $x is [101, 102, Reference#4(index 2)] */
/* $ref remains as Reference#5(index 2) */
$b = $x;
// $b[0] = clone $x[0]; - except $x[0] is an integer so this was automatic
// $b[1] = clone $x[1]; - same
$b[2] = clone $x[2]; // creating a copy of what was in $x[2]
/* $b is [101, 102, Reference#6(index 2)] - a different Reference as $x[2] and $ref but the same underlying value */
$b[0] = 0;
// foreach($x as &$ref) { ... }
/* $x[0] */
$x[0] = new Reference($x[0]); // Reference#7(index 3) = 101
$ref = clone $x[0]; // Reference#8(index 3)
$ref->set($ref->get() + 100); // set index 3 = 201
/* $x[1] */
$x[1] = new Reference($x[1]); // Reference#9(index 4) = 102
$ref = clone $x[1]; // Reference#10(index 4)
$x[0] = $x[0]->get(); // demoted
$ref->set($ref->get() + 100); // set index 4 = 202
/* $x[2] */
// $x[2] = new Reference($x[2]); // - except $x[2] is already Reference#4(index 2)
$ref = clone $x[2]; // Reference#11(index 2)
$x[1] = $x[1]->get(); // demoted
$ref->set($ref->get() + 100); // set index 2 = 203
// end foreach
/* $x is [201, 202, Reference#4(index 2)] */
/* $ref remains as Reference#11(index 2) */
/* $b was not modified during the foreach and still contains [0, 102, Reference#6(index 2)] */
/* however the underlying value of the Reference did change */
// var_dump($b);
var_dump([$b[0], $b[1], $b[2]->get()]);
Enable javascript to submit You have javascript disabled. You will not be able to edit any code.
Output for 5.5.0 - 5.5.35 , 5.6.0 - 5.6.28 , 7.0.0 - 7.0.20 , 7.1.0 - 7.1.33 , 7.2.0 - 7.2.33 , 7.3.0 - 7.3.33 , 7.4.0 - 7.4.33 , 8.0.0 - 8.0.30 , 8.1.0 - 8.1.28 , 8.2.0 - 8.2.18 , 8.3.0 - 8.3.4 , 8.3.6 array(3) {
[0]=>
int(0)
[1]=>
int(102)
[2]=>
int(203)
}
Output for 8.3.5 Warning: PHP Startup: Unable to load dynamic library 'sodium.so' (tried: /usr/lib/php/8.3.5/modules/sodium.so (libsodium.so.23: cannot open shared object file: No such file or directory), /usr/lib/php/8.3.5/modules/sodium.so.so (/usr/lib/php/8.3.5/modules/sodium.so.so: cannot open shared object file: No such file or directory)) in Unknown on line 0
array(3) {
[0]=>
int(0)
[1]=>
int(102)
[2]=>
int(203)
}
preferences:dark mode live preview
203.29 ms | 402 KiB | 258 Q