Bug #68914 [Nab]: Reference survives beyond function scope

From: Date: Mon, 26 Jan 2015 21:17:43 +0000
Subject: Bug #68914 [Nab]: Reference survives beyond function scope
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-190234@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=68914&edit=1 ID: 68914 Updated by: requinix@php.net Reported by: steve dot piner at signify dot co dot nz Summary: Reference survives beyond function scope Status: Not a bug Type: Bug Package: Scripting Engine problem Operating System: Ubuntu 14.10 PHP Version: 5.6.5 Block user comment: N Private report: N New Comment: Poor phrasing on my part: each element *was* a reference, and when the loop moves to the next element the previous is destroyed. At the end the last element remains a reference. However I'm also going along with previous decisions, such as bug #68402, which say that this behavior is not a bug. References can be tricky and unset()ing referenced variables when you're done with them is a good idea. Previous Comments: ------------------------------------------------------------------------ [2015-01-26 20:52:14] steve dot piner at signify dot co dot nz The point isn't that $x survives, the point is that only the last element is a reference, and that it wasn't explicitly converted to a reference. Set $y[1] to 'surprise' and then print out $z[1]: you'll get a result of 2. Only the last element of $x is a reference after the foreach() has exited. The bug is that the last element remains a reference after the referencing variable ($j) has for all intents and purposes ceased to exist. For example, if you add an unset($j); after the foreach(), the issue disappears. ------------------------------------------------------------------------ [2015-01-26 07:00:25] requinix@php.net It survives because $x is static and each member in $x is a reference. $x was initialized once to that range(1,3) array. Whenever f() returns it will return a copy of that array, thus $z and $y have both the same array values even though they are different actual arrays. Modifying $y would have no effect on $z because of the copying... if it weren't for the by-ref foreach you did, which caused each member in the array to become a reference. That makes $x[2], $y[2], and $z[2] all the same so a change made to one of them will "appear" in the others. ------------------------------------------------------------------------ [2015-01-26 05:23:23] steve dot piner at signify dot co dot nz Description: ------------ A reference created with a foreach loop appears to survive long after the function creating the reference has exited. Test script: --------------- function f() { static $x; if(!$x) { $x = range(1, 3); } foreach($x as $i => &$j) { } return $x; } $z = f(); $y = f(); $y[2] = 'surprise'; print $z[2] . "\n"; Expected result: ---------------- 3 Actual result: -------------- surprise ------------------------------------------------------------------------ -- Edit this bug report at https://bugs.php.net/bug.php?id=68914&edit=1

« previous php.bugs (#190234) next »