php的魔術方法__get(),__set(),__call(),__callStatic()以及static用法詳解

來源:互聯網
上載者:User
php5之後實現了一些魔術方法還是比較有意思的,之前一直用面向過程的編程方法,對oop研究的比較少,最近在看oop的東西,還是比較有意思的。

魔術方法這些東西,感覺很大一部分就是為了偷懶用的,記得最早寫php的時候,那時候做部落格,用的是國外的一個叫lifetype的開源架構,那時候還是php4.3,但是那個架構裡全部實現了對象,所有的資料都被封裝到對象中。

於是當從db裡select出來一堆東西之後,還要逐個迴圈封裝成對象,每一個欄位也要實現getField()和getField()方法,寫起來還真有點麻煩,感覺就是在做重複性的工作。

那麼get(),set(),call(),callStatic()這幾個魔術方法的誕生,就完全解決了這個問題。

get()和set()是針對類中屬性的而call()是針對方法的,callStatic() 是針對靜態類的方法。

一、get()和set()魔術方法:

當執行個體化一個對象後,調用類中不存在或者沒有許可權訪問的屬性的時候,php會預設調用get()方法,這樣做,不僅可以少些很多代碼,讓結構更清晰,而且也提供了一條外部存取類的私人成員的一種方法。

比如:

<?phpclass testGet{  private $name = 'test';}$test = new testGet();$test->name;

上面的代碼,如果我們運行,會報一個錯誤:PHP Fatal error: Cannot access private property testGet::$name in /Library/WebServer/Documents/workspace/learn/call/a.php on line 7

但是我們修改一下,通過get()方法就可以訪問

<?phpclass testGet{  private $name = 'test';  function get($property) {    if ( isset($this->$property) )       return $this->$property;    else      return NULL;  }}$test = new testGet();echo $test->name . PHP_EOL;

代碼改成這樣之後我們再訪問就沒有問題。

注意:如果把屬性定義成是static的,那麼通過get()訪問也會報錯。原因是static的成員,是屬於類本身的,不因為執行個體化而改變,可以自己測試。

利用set()方法,可以禁止動態建立類屬性,這樣可以很好的避免給後來開發人員,或者程式維護者帶來不必要的麻煩。

funciton set($property) {

//$property接收的是屬性的名字

}

是實話,oop這個東西的設計,會摻雜很多設計者自己的思想,如果沒有文檔,後來者去讀代碼還是很費勁的,當然和後來者的水平也有很大關係。

下面是一個get和set配合使用的例子:

<?phpclass testGet{  private $name = 'test';  function get($property) {    if ( isset($this->$property) )       return $this->$property;    else      return NULL;  }    public function set($property, $value) {    if ( isset($this->$property) )      $this->$property = $value;    else      return NULL;  }}$test = new testGet();$test->name = 'my test name';echo $test->name . PHP_EOL;

function set($property, $value) {

//$property接收的屬性的名字

//$value接收的是屬性的值

}

二、call()和callStatic()方法:

當對象調用類中一個不存在或者沒有許可權訪問的方法的時候,就會自動調用call()方法。

記得以前有個同事問我,tp架構中為什麼有很多底層的方法沒有,但是在上層還能調用,其實就是call()這個方法在起作用。

如果你不知道這個方法,那麼肯定會很疑惑,而且問題也不好定位。

<?phpabstract class Obj {        private $objData        = array();        /**          * call魔術方法,如果對象請求的方法不存在或者沒有許可權訪問的時候         * 調用魔術方法         */        public function call($name, $args) {            $field = preg_match('/^get(\w+)/', $name, $matches);            if ( $field && $matches[1] )                return $this->objData[strtolower($matches[1])];            $field = preg_match('/^set(\w+)/', $name, $matches);            if ( $field && $matches[1] ) {                 return $this->objData[strtolower($matches[1])] = $args[0];            }           }   }class User extends Obj{        }$user = new User();$user->setName('test');echo $user->getName();

User類什麼都沒幹,但是通過繼承類的call()方法,把所有的事都做了(getName和setName)。

function call($methodName, $args) {

//$methodName調用的方法名

//$args傳遞的參數數組

}

和call()對應的是callStatic()方法,是位靜態類的靜態方法服務的。

例子:

<?php    abstract class Obj     {        private static $objData        = array();        /**          * call魔術方法,如果對象請求的方法不存在或者沒有許可權訪問的時候         * 調用魔術方法         */        public static function callStatic($name, $args) {            $field = preg_match('/^get(\w+)/', $name, $matches);            if ( $field && $matches[1] )                return self::$objData[strtolower($matches[1])];            $field = preg_match('/^set(\w+)/', $name, $matches);            if ( $field && $matches[1] ) {                 return self::$objData[strtolower($matches[1])] = $args[0];            }           }       }    class User extends Obj     {        }    User::setName('test');    echo User::getName() . PHP_EOL;

三、延遲靜態繫結:static這個對象

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.