1. 程式人生 > >9:魔術方法

9:魔術方法

魔術方法的定義

  • 就是那些在某些特定的時刻,會自動執行的方法,統稱為魔術方法。
  • 他們最大的特點是以:__雙下劃線開頭。
  • 例如建構函式,解構函式,克隆函式,__get函式,__set函式,都是魔術方法。

在PHP中系統自帶的函式和方法就有四千多個,記得住嗎???

幾個在專案中很實用的魔術方法

  • __call(),__callStaic(),__get(),__set(),__isset(),__unset()

__get方法

  • 當你呼叫一個許可權上不允許訪問的屬性時,在類中,__get方法就會自動呼叫,方法接受一個引數,引數值是數命名

  • 示例:

class A {
	private $a = 10;
	protected $b = 20;
	public $c = 30;

	public function __get($asd){
		echo '訪問的是' . $asd;
	}
}


$haha = new A();

echo $haha->b;//訪問的是b
  • 作用是,我們可以自己去處理無權訪問屬性的邏輯,比如a和b屬性,當訪問之後,無權訪問,我們可以在__get函式中做一些事;

__set方法

  • 當你為一個物件直接增加一個屬性例如這樣:$a->xiaoming = 20
    ,這個屬性在物件上不存在,在PHP中是直接在物件上增加這個屬性,並賦值,就是:有則重新賦值,沒有先增加再賦值
  • 增加一個不存在的屬性的時候,__set()方法會被呼叫,給你處理物件上不存的屬性被增加時的處理許可權,你可以在set方法中進行處理,可以丟擲錯誤,說不允許新增,也可以什麼都不做,就寫一個空方法,則不可新增新屬性
class A {
	private $a = 10;
	protected $b = 20;
	public $c = 30;

	public function __set($key,$val){
		echo '你新增的屬性是:',$key,'值為:',$val,',但是不允許被新增';
	}
}


$haha = new A();

$haha->d = 20;
var_dump($haha);
//沒有寫set函式的情況下,新屬性被直接新增在了物件上
//寫了set函式的情況,set函式接受兩個引數,第一個引數是新增的屬性的鍵名,第二個引數是新增的屬性的值,一旦寫了set函式,則該物件不再被允許新增新的屬性;
  • 如果是設定已存在的屬性,則set函式不會被觸發,已存在的屬性會被重新賦值

__inset()和__unset()

  • __isset()

    • __isset方法在判斷(protected/private/不存在)的屬性時,就會觸發isset方法執行;
    • isset屬性不可信,因為這個函式的返回值可以被自定義,也就是說,無論你判斷什麼屬性,都可以在isset屬性中返回true,導致判斷屬性是否存在都為真;
  • __unset()

    • unset方法,在釋放一個物件的(protected/private/不存在)的屬性時,會被觸發

在框架是如何應用的

  • 例如,當你在寫一個框架的時候,你需要給框架使用者設計一個物件,這個物件允許使用者自行新增屬性
  • 假如,使用者新增的屬性,在你的物件上存在,怎麼辦?
  • 那麼你就可以用set方法,將使用者新新增的屬性進行梳理,比如將他存在物件中的一個數組中,包括所有的使用者新增的屬性,都放在這個數組裡,這樣就不會和物件自身的屬性發生重名,許可權不夠,覆蓋賦值的問題
  • 而使用者要讀取這個屬性,則可以呼叫get方法,進行處理,判斷陣列中是否存在,有則返回,無則拋錯;
  • 其他的魔術方法,請自己舉一反三,在框架的設計與開發中,應該如何應用?

__call方法

  • 當呼叫例項物件的(protected/private/不存在)的方法或者例項物件的方法呼叫其他方法且滿足這些條件時,會觸發call方法

__callStatic方法

  • 當呼叫例項物件靜態的(protected/private/不存在)的方法或例項物件的方法呼叫自身的靜態方法且滿足這些條件時時,會觸發callStatic方法

PHP中的魔術方法還有很多,不管是自己寫框架還是寫業務,他們都是大有作為的,存在即合理,還有那麼多,自己細細體會吧;