为什么我的 PHP 对象是通过引用传递的
Why are my PHP objects passed by reference
我在 PHP 中看到一些与 reference/assignment 相关的令人困惑的行为...
private function doSomething($things)
{
foreach ($things as $thing) {
echo $thing->property; // 'foobar'
$copyThing = $thing;
unset($copyThing->property);
echo $thing->property; // undefined
我预计在通过引用传递变量时会出现这种行为 (&$thing
),但我并不想在这里这样做,而且它似乎正在发生。我错过了什么?
只是解释一下我的评论:
objects in foreach loops are always passed by reference
当您对对象数组使用 foreach 循环时,您在循环内使用的变量是指向该对象的指针,因此它用作引用,循环内对象的任何更改都是对外面的物体。
这是因为:
objects are always passed by reference (@user3137702 quote)
官方详细解释here.
当您复制并取消设置您的变量时:
$copyThing = $thing;
unset($copyThing->property);
您正在创建另一个指针并将其取消设置,因此原始值已消失。事实上,由于 foreach 循环也使用指针,因此 $things
数组也会受到影响。
检查此 ideone(注意 vardump ['a' 属性 消失了],因为输出与您得到的相同)
我不知道它在哪个版本中改变了,如果有的话,因为它似乎是默认的 object/pointer 行为
解决方法(一些想法):
- 复制你的初始数组
- 使用clone:
$x = clone($obj);
(只要默认复制构造函数适用于您的对象)
我在 PHP 中看到一些与 reference/assignment 相关的令人困惑的行为...
private function doSomething($things)
{
foreach ($things as $thing) {
echo $thing->property; // 'foobar'
$copyThing = $thing;
unset($copyThing->property);
echo $thing->property; // undefined
我预计在通过引用传递变量时会出现这种行为 (&$thing
),但我并不想在这里这样做,而且它似乎正在发生。我错过了什么?
只是解释一下我的评论:
objects in foreach loops are always passed by reference
当您对对象数组使用 foreach 循环时,您在循环内使用的变量是指向该对象的指针,因此它用作引用,循环内对象的任何更改都是对外面的物体。 这是因为:
objects are always passed by reference (@user3137702 quote)
官方详细解释here.
当您复制并取消设置您的变量时:
$copyThing = $thing; unset($copyThing->property);
您正在创建另一个指针并将其取消设置,因此原始值已消失。事实上,由于 foreach 循环也使用指针,因此 $things
数组也会受到影响。
检查此 ideone(注意 vardump ['a' 属性 消失了],因为输出与您得到的相同)
我不知道它在哪个版本中改变了,如果有的话,因为它似乎是默认的 object/pointer 行为
解决方法(一些想法):
- 复制你的初始数组
- 使用clone:
$x = clone($obj);
(只要默认复制构造函数适用于您的对象)