Bug #80161 [Com]: Iterating on key/value with reference (&) has unexpected side effect

From: Date: Tue, 29 Sep 2020 21:10:00 +0000
Subject: Bug #80161 [Com]: Iterating on key/value with reference (&) has unexpected side effect
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-229276@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=80161&edit=1 ID: 80161 Comment by: fghghghgh at fgfgfg dot com Reported by: g dot passault at gmail dot com Summary: Iterating on key/value with reference (&) has unexpected side effect Status: Not a bug Type: Bug Package: Arrays related Operating System: Linux (Ubuntu 18.04) PHP Version: 7.4.10 Assigned To: cmb Block user comment: N Private report: N New Comment: > Imagine foreach($x as $y) would implicitely performs unset($y) beforehand why should it? when should it? everytime after worjing with references no matter what the code after it does? before ? before what exactly? it's a programming language and not supposed to guess what you want you get what you ask for and if you are asking for the wrong thing it's not the fault of the programming language - it's not supposed to guess and introduce runtime overhead to fix common mistakes which can be easily avoided by "do not use references unless you know what you are doing" > that would fix this broken behaviour there is no broken behavior you are using references for no valid reason which don't make sense in a copy-on-write environemnt to begin with - the performance improvement you likely imagined don't exist at all, in most cases the opposite is true when you try to outsmart the zendengine > and what legitimate code would be impacted with such a change? nobody can know at all Previous Comments: ------------------------------------------------------------------------ [2020-09-29 21:02:56] g dot passault at gmail dot com Imagine foreach($x as $y) would implicitely performs unset($y) beforehand, that would fix this broken behaviour, and what legitimate code would be impacted with such a change? ------------------------------------------------------------------------ [2020-09-29 16:05:00] cmb@php.net > However I'm not sure if assigning a value to a variable that is > a reference through the "as" of a foreach is a good behaviour There is nothing special about that assignment; it's a reference assignment, if the variable is already a reference. If you have to use references in foreach loops, and you need the loop variable later on, consider to unset() it after the loop. See also the warning on <https://www.php.net/manual/en/control-structures.foreach.php>. ------------------------------------------------------------------------ [2020-09-29 15:50:30] fghghghgh at fgfgfg dot com there is nothing unexpected, that's how references are working http://schlueters.de/blog/archives/125-Do-not-use-PHP-references.html ------------------------------------------------------------------------ [2020-09-29 15:48:28] g dot passault at gmail dot com Actually, I understand the reason why this behaves like that, since at the end of the first foreach loop $item is a reference to the last item in the array However I'm not sure if assigning a value to a variable that is a reference through the "as" of a foreach is a good behaviour This issue actually happened in a script I wrote and I was surprised with result, what I mean is that I can easily real life example why one would walk an array and change it, and then walk it again to read it, but not real life example of assigning a value with the first iteration of a loop through the "as" of foreach. ------------------------------------------------------------------------ [2020-09-29 15:43:53] g dot passault at gmail dot com Description: ------------ For some reason, walking an array using keys and reference values (&), even without doing anything with it and then walking it has an influence if and only if the variable name is the same in both cases Test script: --------------- <?php $array = [ 'x' => 1, 'y' => 2, 'z' => 3 ]; // This useless walk has an effect on below walk foreach ($array as &$item) {} // This will show 1 2 2 instead of 1 2 3 // If you use another name for $item variable, it will show 1 2 3 foreach ($array as $item) { echo $item."\n"; } Expected result: ---------------- 1 2 3 Actual result: -------------- 1 2 2 ------------------------------------------------------------------------ -- Edit this bug report at https://bugs.php.net/bug.php?id=80161&edit=1

« previous php.bugs (#229276) next »