PHP中的“=&”和“&=”运算符是什么意思?

PHP中的“=&”/“&=”运算符是什么意思? 我在哪里可以阅读关于他们的信息?

搜索谷歌没有帮助。


$a &= $b$a = $a & $b简称,它是按位运算符。

$a =& $b$a =& $b分配给$ b的引用。


=

$a =& $b$a转换为$b的别名。 如果$a的值或引用发生更改, $b的值或引用将相应更改。

这与“指向同一地点”的对象不同:我可以做$c = $d = new AnObject( ),并且这两个变量都指向相同的地方; 然而,改变其中一点不会改变其他点的地方。 也就是说, $c = null不会使$d = null 。 然而,在$a =& $b的情况下, $a = null会使$b = null

注意:正式地,别名实际上被称为引用。 官方术语有点不恰当,并且肯定含糊不清,所以我选择使用术语“别名”来代替。 有关文档,请参阅php.net。

用途和效果

对于标量值, =&就像是将值包装在一个对象中,以便您可以在多个变量之间普遍地更改该值。 对于通常通过引用传递的类型(对象), =&提供对引用的引用。

我倾向于在使用关联数组时使用=& 。 我可以创建一个别名: $foobar =& $foo['bar']['foobar']而不是重写$foo['bar']['foobar'] $foobar =& $foo['bar']['foobar'] 。 如果索引不存在,这些工具甚至可以工作。 如果$foo['bar']['foobar']不存在,则isset($foobar)将为false。 这比使用普通的旧变量要好,因为我可以在测试密钥的存在之前创建别名,而不会触发错误。

只要确保在完成后取消设置( unset($foobar) )别名即可。 否则,如果稍后重用变量名称,则最终将覆盖别名指向的任何内容。

您也可以以其他方式使用别名 - 他们不限于分配。 他们与:

  • foreach循环: foreach ($a as &$b)分配给$b将覆盖在相应的值$a 。 完成后请取消$b ,否则会遇到奇怪的问题!
  • 功能/方法参数: function foobar(&$a)分配到$afoobar会改变任何可变的呼叫者与传递$a
  • 函数/方法返回值: function &foobar()返回的内容可以被调用者修改; 这对于传递别名很有用。 滥用也很容易。
  • 数组: $a = array(&$b)$a[0]任何更改现在都会影响$b ,包括赋值。
  • call_user_func_array: call_user_func('foobar', array(&$a))假设foobar接受一个别名参数, foobar现在可以修改$a 。 这允许你使用call_user_func_array调用带有别名参数的函数/方法。
  • 例子

    标量

    $original = 1;
    $copy = $original;
    $reference =& $original;
    // All three variables == 1.
    
    $reference = 2;
    // $original == 2, $reference == 2, $copy == 1
    
    $original = 3;
    // $original == 3, $reference == 3, $copy == 1
    
    $copy = 4;
    // $original == 3, $reference == 3, $copy == 4
    

    对象

    #!/usr/bin/env php
    <?php
    class Object
    {
            private $properties;
    
            public function __construct(array $properties = array())
            {
                    $this->properties = $properties;
            }
    
            public function __isset($key)
            {
                    return isset($this->properties[$key]);
            }
    
            public function __unset($key)
            {
                    unset($this->properties[$key]);
            }
    
            public function __get($key)
            {
                    return isset($this->$key) ? $this->properties[$key] : null;
            }
    
            public function __set($key, $value)
            {
                    $this->properties[$key] = $value;
            }
    
            public function __toString()
            {
                    return print_r($this->properties, true);
            }
    }
    
    function print_vars()
    {
            global $original, $ref, $refref;
    
            echo
                    '$original: ', $original,
                    '$ref: ', $ref,
                    '$refref: ', $refref,
                    PHP_EOL;
    }
    
    $original = new Object(array('a' => 1, 'b' => 2, 'c' => 3));
    $ref = $original;
    $refref =& $original;
    print_vars();
    /*
    $original: Array
    (
        [a] => 1
        [b] => 2
        [c] => 3
    )
    $ref: Array
    (
        [a] => 1
        [b] => 2
        [c] => 3
    )
    $refref: Array
    (
        [a] => 1
        [b] => 2
        [c] => 3
    )
    */
    
    $original->a = 'duck';
    $ref->b = 'moose';
    $refref->c = 'cow';
    print_vars();
    /*
    $original: Array
    (
        [a] => duck
        [b] => moose
        [c] => cow
    )
    $ref: Array
    (
        [a] => duck
        [b] => moose
        [c] => cow
    )
    $refref: Array
    (
        [a] => duck
        [b] => moose
        [c] => cow
    )
    */
    
    // This carries over to $refref, but not $ref.
    $original = new Object(array('x' => 1, 'y' => 2, 'z' => 3));
    print_vars();
    /*
    $original: Array
    (
        [x] => 1
        [y] => 2
        [z] => 3
    )
    $ref: Array
    (
        [a] => duck
        [b] => moose
        [c] => cow
    )
    $refref: Array
    (
        [x] => 1
        [y] => 2
        [z] => 3
    )
     */
    
    // This does *not* carry over to $original or $ref.
    $ref = new Object(array('o' => 42, 'm' => 123, 'n' => 1337));
    print_vars();
    /*
    $original: Array
    (
        [x] => 1
        [y] => 2
        [z] => 3
    )
    $ref: Array
    (
        [o] => 42
        [m] => 123
        [n] => 1337
    )
    $refref: Array
    (
        [x] => 1
        [y] => 2
        [z] => 3
    )
    */
    
    // This *does* carry over to $original, but not $ref.
    $refref = new Object(array('alpha' => 10, 'beta' => 20, 'gamma' => 30));
    print_vars();
    /*
    $original: Array
    (
        [alpha] => 10
        [beta] => 20
        [gamma] => 30
    )
    $ref: Array
    (
        [o] => 42
        [m] => 123
        [n] => 1337
    )
    $refref: Array
    (
        [alpha] => 10
        [beta] => 20
        [gamma] => 30
    )
    */
    ?>
    

    &=

    &=无关=& 。 它来自一组赋值操作。 这只是一些:

  • +=
  • -=
  • *=
  • /=
  • 看到这里的趋势?

    二进制算术运算符通常具有赋值对应项。 假设@是一个算术运算符(它不是写作),因此当$a$b是数字时, $a @ $b通常会产生一个数字。 (认为​​:加法,乘法,除法等)你需要多久做一次这样的事情?

    $a = $a @ $b;
    

    很经常。 重复$a似乎没有必要吗? 包括PHP在内的许多语言都使用一组赋值运算符来解决这个问题:

    $a @= $b;
    

    简单得多,对于习惯于这种表示法的程序员来说,一眼就可能更简洁和描述性。 (我当然觉得阅读起来比较容易,因为我很习惯。)所以要加倍变量:

    $a *= 2;
    

    快速,简单,相对描述性强。 包括PHP在内的一些语言将这个特性扩展到算术之外,以实现额外的一两个操作。 值得注意的是:

    $a = $a . 'Appended text';
    // Is the same as:
    $a .= 'Appended text';
    

    很有用。

    &=落在这些赋值运算符之间,因为&表示按位运算与运算。 PHP文档中还列出了其他一些内容(请参阅前面提到的链接),所有这些对许多编程语言都是通用的。

    这意味着$a &= $b$a = $a & $b

    链接地址: http://www.djcxy.com/p/1711.html

    上一篇: What do the "=&" and "&=" operators in PHP mean?

    下一篇: Reference assignment operator in PHP, =&