首頁 >後端開發 >PHP問題 >php中魔術方法和魔術常數是什麼

php中魔術方法和魔術常數是什麼

青灯夜游
青灯夜游原創
2021-06-21 18:14:572717瀏覽

在php中,魔術方法是指以兩個底線「__」開頭的方法,例如「__call()」、「__get()」、「__set()」等;魔術常數是指會隨著他們所在代碼位置的變化而變化的8個常數,例如“__LINE__”、“__FILE__”等。

php中魔術方法和魔術常數是什麼

本教學操作環境:windows7系統、PHP7.1版,DELL G3電腦

魔術方法(Magic methods)

PHP中把以兩個底線__開頭的方法稱為魔術方法,這些方法在PHP中充當了舉足輕重的作用。魔術方法包括:

  • __construct(),類別的建構子
  • ##__destruct(),類別的析構函式
  • __call(),在物件中呼叫一個不可存取方法時呼叫
  • #__callStatic(),用靜態方式中呼叫一個不可存取方法時呼叫
  • __get(),當取得一個類別的成員變數時呼叫
  • __set(),設定一個類別的成員變數時呼叫
  • __isset(),當對不可存取屬性呼叫isset()empty()時呼叫
  • __unset(),當對不可存取屬性呼叫unset()時被呼叫。
  • __sleep(),執行serialize()時,先會呼叫這個函數
  • __wakeup(),執行unserialize()時,先會呼叫這個函數
  • __toString(),類別被當成字串時的回應方法
  • __invoke(),呼叫函數的方式呼叫一個物件時的回應方法
  • __set_state(),呼叫var_export()匯出類別時,此靜態方法會被呼叫。
  • __clone(),當物件複製完成時呼叫

#__construct()__destruct()

建構子和析構函式應該不陌生,他們在物件建立和消亡時被呼叫。例如我們需要打開一個文件,在物件建立時打開,物件消亡時關閉

<?php 
class FileRead
{
    protected $handle = NULL;

    function __construct(){
        $this->handle = fopen(...);
    }

    function __destruct(){
        fclose($this->handle);
    }
}
?>

這兩個方法在繼承時可以擴展,例如:

<?php 
class TmpFileRead extends FileRead
{
    function __construct(){
        parent::__construct();
    }

    function __destruct(){
        parent::__destruct();
    }
}
?>

__call ()__callStatic()

在物件中呼叫一個不可存取方法時會呼叫這兩個方法,後者為靜態方法。這兩個方法我們在可變方法(Variable functions)呼叫中可能會用到。

<?php
class MethodTest 
{
    public function __call ($name, $arguments) {
        echo "Calling object method &#39;$name&#39; ". implode(&#39;, &#39;, $arguments). "\n";
    }

    public static function __callStatic ($name, $arguments) {
        echo "Calling static method &#39;$name&#39; ". implode(&#39;, &#39;, $arguments). "\n";
    }
}

$obj = new MethodTest;
$obj->runTest(&#39;in object context&#39;);
MethodTest::runTest(&#39;in static context&#39;);
?>

__get()__set()__isset()__unset()

#當get/set一個類別的成員變數時呼叫這兩個函數。例如我們將物件變數保存在另外一個陣列中,而不是物件本身的成員變數

<?php 
class MethodTest
{
    private $data = array();

    public function __set($name, $value){
        $this->data[$name] = $value;
    }

    public function __get($name){
        if(array_key_exists($name, $this->data))
            return $this->data[$name];
        return NULL;
    }

    public function __isset($name){
        return isset($this->data[$name])
    }

    public function unset($name){
        unset($this->data[$name]);
    }
}
?>

#__sleep()__wakeup()

#當我們在執行

serialize()unserialize()時,就會先呼叫這兩個函數。例如我們在序列化一個物件時,這個物件有一個資料庫鏈接,想要在反序列化中恢​​復連結狀態,則可以透過重構這兩個函數來實現連結的恢復。範例如下:
<?php
class Connection 
{
    protected $link;
    private $server, $username, $password, $db;

    public function __construct($server, $username, $password, $db)
    {
        $this->server = $server;
        $this->username = $username;
        $this->password = $password;
        $this->db = $db;
        $this->connect();
    }

    private function connect()
    {
        $this->link = mysql_connect($this->server, $this->username, $this->password);
        mysql_select_db($this->db, $this->link);
    }

    public function __sleep()
    {
        return array(&#39;server&#39;, &#39;username&#39;, &#39;password&#39;, &#39;db&#39;);
    }

    public function __wakeup()
    {
        $this->connect();
    }
}
?>

__toString()

物件當成字串時的回應方法。例如使用echo $obj;

來輸出一個物件

<?php
// Declare a simple class
class TestClass
{
    public function __toString() {
        return &#39;this is a object&#39;;
    }
}

$class = new TestClass();
echo $class;
?>
這個方法只能傳回字串,而且不可以在這個方法中拋出異常,否則會出現致命錯誤。

__invoke()

在呼叫函數的方式呼叫一個物件時的回應方法。如下

<?php
class CallableClass 
{
    function __invoke() {
        echo &#39;this is a object&#39;;
    }
}
$obj = new CallableClass;
var_dump(is_callable($obj));
?>

__set_state()

#呼叫

var_export()

匯出類別時,此靜態方法會被呼叫。
    <?php
    class A
    {
        public $var1;
        public $var2;
    
        public static function __set_state ($an_array) {
            $obj = new A;
            $obj->var1 = $an_array[&#39;var1&#39;];
            $obj->var2 = $an_array[&#39;var2&#39;];
            return $obj;
        }
    }
    
    $a = new A;
    $a->var1 = 5;
    $a->var2 = &#39;foo&#39;;
    var_dump(var_export($a));
    ?>
  • __clone()
  • #當物件複製完成時呼叫。例如在
  • 設計模式詳解及PHP實作:單例模式一文中提到的單例模式實作方式,利用這個函數來防止物件被複製。
  • <pre class="brush:php;toolbar:false;">&lt;?php public class Singleton { private static $_instance = NULL; // 私有构造方法 private function __construct() {} public static function getInstance() { if (is_null(self::$_instance)) { self::$_instance = new Singleton(); } return self::$_instance; } // 防止克隆实例 public function __clone(){ die(&amp;#39;Clone is not allowed.&amp;#39; . E_USER_ERROR); } } ?&gt;</pre>
  • 魔術常數(Magic constants)
  • PHP中的常數大部分都是不變的,但是有8個常數會隨著他們所在代碼位置的變化而變化,這8個常數稱為魔術常數。
  • __LINE__
  • ,檔案中的目前行號
  • #__FILE__
  • ,檔案的完整路徑和檔案名稱
  • __DIR__
  • ,檔案所在的目錄
  • __FUNCTION__
  • #,函數名稱

__CLASS__

,類別的名稱

__TRAIT__###,Trait的名字#########__METHOD__###,類別的方法名稱########__NAMESPACE__####,目前命名空間的名稱# ########這些魔術常數常被用來取得目前環境資訊或記錄日誌。 ######推薦學習:《###PHP影片教學###》###

以上是php中魔術方法和魔術常數是什麼的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn