看了php手冊中關於後期靜態繫結,還是不太明白,原文地址 http://cn2.php.net/manual/zh/language.oop5.late-static-bindings.php
其中第四個例子
結果是:
A
C
C
當調用到parent::foo()和self::foo()時,為什麼會調用C類的who()?
哪位朋友能解釋一下,謝謝。
回複討論(解決方案)
關於static操作符的解釋:
後期靜態繫結試圖通過引入一個關鍵字表示運行時最初調用的類來繞過限制。
而這個最初調用的類就是C
A::foo(); 調用的是A類的方法,這你明白
self::foo(); // 這個self實際上是C類。明白嗎? C::test() C繼承了B的test()方法
parent::foo(); // 由於static::who(); 而不是self::who()。該方法調用的當前的類,也就是C類的foo()方法
也許你覺得還是弄不懂 A類中又為什麼沒有調用C的who()方法,這是由於parent的特殊關係。延遲靜態繫結就是專門為瞭解決子類與父類間繼承方法的問題才出現的。
也不必死記這個概念或者情景,當你遇到一個靜態函數的繼承與覆蓋問題的時候,並發現它不是你想象中樣子,那麼你加上static再試一下成功了,就OK了。
個人感覺物件導向語言的特性比較個人化,而基本的東西無非封裝,多態和繼承,更多變態的特性一般是沒有需求的,需求的時候也得考慮是不是可靠值得信賴。
手冊不是說得很清楚麼
------------------------------------------------------
”後期綁定“的意思是說,static::不再被解析為定義 當前方法所在的類,而是在實際運行時計算的。也可以稱之為”靜態繫結“,因為它可以用於(但不限於)靜態方法的調用。
-------------------------------------------------------
#1說的有個小問題
self::foo(); // 這個self實際上是C類。明白嗎? C::test() C繼承了B的test()方法
不準確,self還是B類,但是本身沒有覆寫foo方法,所以就調用父類A的foo方法。
如果self實際是C類,那你試下self::foo();改成self::who();,應當列印C,但是列印B,這也正是self和static的區別。
謝謝糾正,學習了 手冊不是說得很清楚麼
------------------------------------------------------
”後期綁定“的意思是說,static::不再被解析為定義當前方法所在的類,而是在實際運行時計算的。也可以稱之為”靜態繫結“,因為它可以用於(但不限於)靜態方法的調用。
----------------------------------------------……
A::foo(); //A指代A類,訪問A類的foo方法和who方法
parent::foo();//調用B類的父類??A的foo方法,並告訴foo方法最原始的調用者是C
self::foo(); //self指代定義該方法的類,即B,但是B沒有定義foo方法,它將原始的調用者C向上傳遞,
// 訪問父類的foo方法,最後訪問c的who方法;
所以這就回答了三樓的疑問:若是把self::foo(); 改成self::who,因為self指代B,而B有who方法,所以結果是變成了B
靜態調用使用 parent:: 或者 self:: 將轉寄原始調用資訊。