【引用是什麼】php
PHP中的引用是用不一樣的名字訪問同一個變量內容。不一樣與C的指針,PHP中的引用是zval標識符的別名。ide
1 //對未定義的變量進行引用賦值、引用參數傳遞或引用返回時,將自動建立該變量 2 function refTst(&$var){ 3 var_dump($var); 4 } 5 6 refTst($a); //$a自動被建立並賦值爲NULL 7 8 refTst($ary['k']); 9 var_dump(array_key_exists('k',$ary)); //bool(true) 10 11 $obj=new StdClass(); 12 refTst($obj->p); 13 var_dump(property_exists($obj,'p')); //bool(true)
1 //函數內引用全局變量 2 function globalRef(){ 3 global $var1,$var2; //global $var是$var=&$GLOBALS['var']的簡寫 4 5 $var2=$var1; 6 echo $var2,$GLOBALS['var2'],PHP_EOL; //11 7 8 $var2=2; 9 echo $var2,$GLOBALS['var2'],PHP_EOL; //22 10 11 $var2=&$var1; 12 echo $var2,$GLOBALS['var2'],PHP_EOL; //12 13 14 $var2=3; 15 echo $var2,$GLOBALS['var2'],PHP_EOL; //32 16 echo $var1,$GLOBALS['var1'],PHP_EOL; //33 17 } 18 19 $var1=1; 20 $var2=0; 21 globalRef();
【引用傳參】函數
1 //引用傳參 2 function refTst(&$var){ 3 ++$var; 4 } 5 6 $var=1; 7 refTst($var); //若是寫成refTst(&$var)將出現FATAL_ERROR。解決方法是設置php.ini中allow_call_time_pass_reference=true 8 echo $var; //2 9 10 call_user_func_array('refTst',array(&$var)); //第二個參數中必須加&,不然出現E_WARNING。call_user_func()中的參數不能是引用。 11 echo $var; //3
【引用返回】this
1 //引用返回 2 function &refReturn{ 3 static $var=0; 4 ++$var; 5 return $var; 6 } 7 8 $v=refReturn() //$v不是函數的引用返回,跟普通函數調用同樣。$v和$val的值都是1 9 $v=5; //$var任然是1 10 $v=refRetrun() //$v和$val的值都是2 11 12 $v=&refReturn() //引用返回的正確調用格式,$v是$var的引用。$v和$var都是3 13 $v=5; //$v和$var都是5 14 $v=refReturn(); //$v和$var都是6
1 class Talker{ 2 private $data='Hi'; 3 4 public function & get(){ 5 return $this->data;//不是return($this->data); 6 } 7 8 public function out(){ 9 echo $this->data; 10 } 11 } 12 13 $obj=new Talker(); 14 $dt=&$obj->get(); 15 16 $obj->out(); 17 18 $dt=' ,How'; 19 $obj->out(); 20 21 $dt=' Are'; 22 $obj->out; 23 24 $dt=' You!'; 25 $obj->out; 26 27 //運行結果 28 Hi,How Are You!
【對象的引用】spa
1 class Cls{ 2 public $data='Obj Data'; 3 } 4 5 $obj=new Cls(); 6 echo obj->data; //Obj Data 7 $obj1=$obj; //PHP5中對象賦值是個引用過程(PHP4中是個拷貝過程),PHP5默認以引用方式調用對象。若要創建對象副本,能夠重寫其__clone()方法; 8 $obj1->data='Obj1 Data'; 9 echo $obj->data; //Obj1 Data
【寫時拷貝】指針
PHP中對地址的指向功能是由Zend核心實現的,PHP採用的是寫時拷貝的原理,即:除非發生寫操做,不然指向同一個地址的變量或對象是不會被拷貝的。code
1 //寫時拷貝 2 $ary=array('a','b','c'); 3 $ary1=$ary; //程序運行到這裏,$ary和$ary1都指向同一塊內存。 4 5 function getAryCnt(&$ary){ 6 echo count($ary); 7 } 8 getAryCnt($ary); //經過引用將$ary傳遞給getAryCnt()函數。此時,Zend引擎會認爲getAryCnt()可能會改變$ary,因此此時將爲$ary1從新申請一塊內存單元並保存$ary的數據拷貝。這個過程就是「寫時拷貝」。 9 10 //修改getAryCnt() 11 function getAryCnt($ary){ 12 echo count($ary); 13 } 14 getAryCnt($ary); //將getAryCnt()改成非引用傳參時,不會改變$ary的值,因此沒有出現寫時拷貝。
【取消引用】對象
1 //取消引用用unset()實現 2 error_reptting(0); 3 function refTst(){ 4 $var=&$GLOBALS['var']; //等同於global $var; 5 $var=5; 6 unset($var); //只是消除$var的引用,而對全局變量$GLOBALS['var']沒影響 7 var_dump($var); //NULL 8 echo $GLOBALS['var']; //5 9 } 10 11 $var=1; 12 refTst(); 13 echo $var; //5