• foreach引用坑


    先看下面代码

    $arr1 = [1, 2];
    
    foreach($arr1 as $key => $value) {
      $value = $value + 1;
    }
    
    var_dump($key, $value); //结果输出1,3

    说明:在上面的foreach循环中,当循环结束后,临时变量 $key和$value变量都不会被自动释放掉。值会被保存下来。而且此时修改$val的值不会影响$arr。

    理解foreach的原理,对上面的结果不难理解,foreach循环时,每次循环就会把`$arr1`元素的值复制给临时变量:$key, $value。如,第一次循环时,如下

    $key = 0;
    $value = $arr1[0];

    第二次循环时,如下

    $key = 1;
    $value = $arr1[1];

    再看forach中使用引用

    引用:如果想在遍历数组的过程中修改数组的元素,可以在foreach中对$val使用引用。此时被引用的元素$val指向当前数组元素的内存地址,即共享一段内存地址。因此修改$val的值会同时改变$arr[$key]的值。

    $arr1 = [1, 2];
    foreach($arr1 as $key => $value) {
        $value = $value + 1;
    }
    var_dump($key, $value); //结果输出1,3

    var_dump($arr1);
    $arr1 的值 为 ['0' => 2, '1' => 3]

    说明:$key , $value 的值和上面的非引用情况下一样。在foreach中使用&引用后,当foreach结束后,$key和$val变量也都不会被自动释放掉,但是此时$val和$arrcount($arr) - 1指向相同的内存地址。因此,此时修改$val的值也会改变了$arr[3]的值。

    foreach 引用时,原理和上面一样,只不过是引用复制,原来如下

    第一次循环:
    $key = 0;
    $value =  &$arr1[0];
    
    第二次循环:
    $key = 1;
    $value =  &$arr1[1];

    再看个例子:

    $arr1 = [1, 2];
    foreach($arr1 as $key => &$value) {
        $value = $value + 1;
    }
    var_dump($arr1);
    
    $value = 100;
    
    var_dump($arr1);

    第二次输出 $arr1时,第二个元素的值也是100了。

    理解了原理,就知道坑了。如果我们2个foreach循环,使用相同的临时变量就会有问题了,一个foreach在使用引用的时候。

    如:

    $arr1 = [1, 2];
    foreach($arr1 as $key => &$value) {
        $value = $value + 1;
    }
    //此时 $value = &$arr1[1] ,后面改变$value的值就会改变$arr1[1]元素的值。
    $arr2 = [10, 20, 30]; foreach ($arr2 as $value) { var_dump($arr1); }

    我们发现在循环$arr2时,$arr2元素复制给$value后,同时$arr1的最后一个元素的值也发生变化,此时等于$arr2此时指针对应元素的值。依次推,$arr1最后一个元素的值 = $arr2元素的最后一个值。

    解决方法,使用unset()释放元素, 或者循环第2个数组的时候,使用不同的临时变量

    $arr1 = [1, 2];
    foreach($arr1 as $key => &$value) {
        $value = $value + 1;
    }
    unset($value);
    $arr2 = [10, 20, 30];
    foreach ($arr2 as $value) {
        var_dump($arr1);
    }



  • 相关阅读:
    在线教育02
    HashMap如何解决取Value值为Null
    Java+selenium 如何定位下拉框select
    Java+selenium 如何下拉移动滚动条【实战】
    Python创建第一个django应用
    如何在Pycharm中配置Python和Django(环境搭建篇)
    selenium+iframe 如何定位元素(实战)
    Java+Selenium 如何参数化验证Table表格数据
    如何实现一个字符的反转 (Java)
    Feature如何解决参数数量不匹配
  • 原文地址:https://www.cnblogs.com/echojson/p/12057354.html
Copyright © 2020-2023  润新知