author: selfimpr
blog: http://blog.csdn.net/lgg201
mail: [email protected]
本文博客地址: http://blog.csdn.net/lgg201/archive/2011/04/10/6313362.aspx相关问题: http://topic.csdn.net/u/20110407/03/f72cdfc2-7424-42d0-ba9e-3b8fbef137d7.html?23430首先说变量的名称空间, 名称空间有全局名称空间, 局部名称空间(函数内部/方法内部), 所谓名称空间, 就是存放名字的地方, 就是一个符号表, 你可以想象, 有很多数组, 专门用来存放自己作用域中的名字.每个名称空间是相互隔离的, 它们各自维护一个符号表用来保存自己作用域中的名称(变量名)变量是由名字和值组成的. 上面的名称空间中保存了变量的名字, 变量的值有两种类型, 一种是直接的值, 另外一种是对其他变量的引用.按照楼主的意思, 应该是明白引用的含义的, 不再赘述.php中引用的用法:
1. 变量的引用赋值: $a = &$b
2. 函数调用时的引用参数传递
    1) 早期php是在调用时通过&符号传递引用类型的变量, 比如: func(&$arg);
    2) 后来, 函数的引用类型参数被规定为需要在函数声明时定义, 不如: function func(&$arg);
       注: 引用声明时定义引用类型参数后, 运行时引用参数传递被废弃, 需要在php.ini中增加allow_call_time_pass_reference来开启.
3. 函数返回引用类型, 这种应用方式需要声明函数时, 在函数名前增加&符号, 并且, 在调用时, 要用引用赋值方式, 比如:
function &func() {
    return $a;
}
$a = func();  //这种调用方式得到的不是引用传值
$a =& func(); //这样调用才是引用传值
    简而言之, 就是让函数的返回一个引用类型的值, 一个更实际的例子:
$a = 1;
function &func(&$a) {
  return $a;
}
$b = func($a);
$c =& func($a);
$b = 2;
echo "a: $a, b: $b, c: $c. <br />\n";
//输出a: 1, b: 2, c: 1.
//可见对$b的修改不会影响$a
$c = 3;
echo "a: $a, b: $b, c: $c. <br />\n";
//输出a: 3, b: 2, c: 3.
//可见对$c的修改会影响$a4. global和static两个关键字
  1) global用来声明函数内部要使用一个全局变量, 其实这里隐式的创建了一个引用, 比如, global $a;就是在本地名称空间中创建一个名字a, 让它指向全局空间中$a变量的值.
  2) static关键字也是隐式创建了一个引用, 这里谈的static是指在函数内部声明静态变量的用法, 比如
function func() {
  static $a = 1;
  echo $a ++ . ", ";
}
while($a ++ < 10) func();
//输出结果: 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
这种用法会在一次请求(就是php一次完整的解释执行)过程中, 该变量只会被初始化一次, 每次函数调用结束后, 函数内的静态变量不会被销毁(而其他的局部变量会被销毁), 下一次函数调用时, 又重复利用上一次处理后的结果.

解决方案 »

  1.   

    呵呵,这个解析比较详细……php的引用确实要脑子转点弯
      

  2.   

    有时候参数引用的时候会出问题,有时又没事,PHP手册也这么说,但没说原因
      

  3.   


    老大说的是! 不如手册说的明白http://www.php.net/manual/zh/language.references.php
      

  4.   

    较真的话,需追踪ZE的变量实现机制php是弱类型语言,而C确实强类型语言,在处理变量的时候,是怎么解决这个问题的呢?有兴趣的,了解下php源码Zend/zend.h里,对_zval_struct结构体成员zvalue_value的定义为了简单说明下问题,请看$val = str_repeat('a', 1024);
    echo memory_get_usage(), '<br />';
    $value = $val;/*①*/
    echo memory_get_usage(), '<br />';
    $value = str_repeat('b', 1024);
    echo memory_get_usage(), '<br />';
    而当①处代码改成$value = &$val;再次执行=============================================================================比较两次打印数据,就能从结果发现,php中&指向的是同一块内存空间,这样的结果使得改变$value值,$val值也会随之改变,因为$value,$val的值最终保存在内存的一个地方而没有&的赋值则不会,这会开辟一个新的内存空间来保存$value值,使得当$value赋予新值时,内存增加了1K多。而这种情况代码执行到①后,并不会立刻开辟新的空间,这也是ZE节省服务器资源、提高效率的措施之一更深入的了解,需要更深的读ZE机制这里是从结果去分析原理,有点本末倒置的感觉
    欢迎大家探讨,指正!
      

  5.   


    恩, 呵呵, 结合zval机制更好说明...不过这个帖子其实是看文中提到的问题时, 所想的一些...所以, 就这样了...见笑了..