PHP 매직 메소드:
__construct(), __destruct(), __call(), __callStatic(), __get(), __set(), __isset(), __unset(), __sleep(), __wakeup(), __toString(), __invoke(), __set_state(), __clone() 및 __debugInfo()와 같은 메서드는 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()
객체가 생성될 때 생성자 __construct()가 호출되고 객체가 종료될 때 소멸자 __destruct()가 호출됩니다. 🎜>
<?php   class ConDes {     protected $a = '';     function __construct(){         echo '在构造函数中<br>'; } function __destruct(){ echo '在析构函数中<br>'; } } $val = new ConDes(); unset($val); ?><pre name="code" class="php">
<?php class MethodTest { public function __call ($name, $arguments) { var_dump($arguments); echo "object method $name and ".implode(',',$arguments)."<br>"; } public static function __callStatic ($name, $arguments) { echo "static method $name and ".implode(',',$arguments)."<br>"; } } $obj = new MethodTest; $obj->runTest('in object context','another arg'); MethodTest::runTest('in static context'); ?>
0 => 문자열 '객체 컨텍스트'(길이=17)
1 => 문자열 '다른 인수'(길이=11)
객체 메서드 runTest 및 in 객체 컨텍스트, 또 다른 인수
정적 메서드 runTest 및 정적 컨텍스트
에서 액세스할 수 없는 클래스 멤버를 가져올 때 이 두 함수가 호출됩니다. 액세스할 수 없는 클래스 멤버 변수를 설정할 때. <br><br>
출력:<?php class MethodTest { private $data = array(); private $a = ''; public $bbb = ''; public function __set($name, $value){ $this->data[$name] = $value; echo '__set'; var_dump($this->data); } public function __get($name){ echo '__get'; var_dump($this->data); if(array_key_exists($name, $this->data)) return $this->data[$name]; return NULL; } public function __isset($name){ echo '__isset'; return isset($this->data[$name]); } public function __unset($name){ echo '__unset'; unset($this->data[$name]); } } $in = new MethodTest(); $in->a = 'aaaa'; $aaa = $in->a; $res = isset($in->c)? 'set':'not set'; echo '<br>'.$res.'<br>'; unset($in->a); ?>
배열(크기=1)
'a' => 문자열 'aaaa'(길이=4)
__get
배열(크기=1)
'a' = > string 'aaaa' (길이=4)
__isset
설정되지 않음
__unset
serialize()를 실행할 때 및 unserialize할 때 (), 이 두 함수가 먼저 호출됩니다. 예를 들어, 객체를 직렬화할 때 객체에 데이터베이스 링크가 있습니다. 역직렬화 중에 링크 상태를 복원하려면 이 두 함수를 재구성하여 링크를 복원할 수 있습니다.
<p><code><span></span>
<?php class Connection {     public $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() { echo 'sleep<br>'; return array('server', 'username', 'password', 'db'); } public function __wakeup() { echo 'wakeup<br>'; $this->connect(); } } $a = new Connection('localhost','mosi','moshi','test'); $sql = 'select id,username from user limit 1'; $res = mysql_query($sql,$a->link); $res = mysql_fetch_array($res); var_dump($res); $sres = serialize($a); mysql_close($a->link); //unset($a); $unsres = unserialize($sres); var_dump($unsres); $sql = 'select id,username from user limit 1'; $ress = mysql_query($sql,$unsres->link); $ress = mysql_fetch_array($ress); var_dump($ress); ?>
<code><span>array (size=4)<br> 0 => string '1' (length=1)<br> 'id' => string '1' (length=1)<br> 1 => string 'm0sh1' (length=5)<br> 'username' => string 'm0sh1' (length=5)<br>sleep<br>wakeup<br>object(Connection)[2]<br> public 'link' => resource(6, mysql link)<br> private 'server' => string 'localhost' (length=9)<br> private 'username' => string 'moshi' (length=4)<br> private 'password' => string 'moshi' (length=5)<br> private 'db' => string 'test' (length=4)<br>array (size=4)<br> 0 => string '1' (length=1)<br> 'id' => string '1' (length=1)<br> 1 => string 'm0sh1' (length=5)<br> 'username' => string 'm0sh1' (length=5)</span>
배열(크기=4)
'id' => 문자열 '1'(길이=1) 1 => 문자열 'm0sh1'(길이=5)
sleep<span>__toString()<br>对象当成字符串时的回应方法。例如使用echo $obj;</span>
wakeup
공개 '링크' => 리소스(6, mysql 링크)<span></span>
비공개 '서버' => 문자열 'localhost'(길이=9)
<?php class TestClass { public function __toString() { return 'this is a object'; } } $class = new TestClass(); echo $class; ?>
개인 'db' => 문자열 '테스트'(길이=4)<span></span>
배열(크기 =4) )<span></span>
0 => 문자열 '1'(길이=1)
1 => 문자열 'm0sh1' )
'사용자 이름' => 문자열 'm0sh1'(길이=5)
<?php class Invoke{ public function __invoke(){ echo 'in invoke<br>'; } } class noInvoke{ } $obj = new Invoke(); $obj(); var_dump(is_callable($obj)); $obj2 = new noInvoke(); //$obj2(); var_dump(is_callable($obj2));
<p>__toString ()<br>객체를 문자열로 처리할 때의 응답 방식입니다. 예를 들어 echo $obj;<br></p>
<br><br>
<?php class A { public $var1; public $var2; public static function __set_state ($arr) { $obj = new A; $obj->var1 = 'var11'; $obj->var2 = $arr['var2']; return $obj; } } $a = new A; $a->var1 = 5; $a->var2 = 'foo'; var_dump($a); var_export($a); eval('$ress = '.var_export($a,true).';'); var_dump($ress); ?>
<br><br>
이것은 객체입니다<br><br>이 메서드는 문자열만 반환할 수 있으며 Throw할 수 없습니다. 이 메서드에서는 예외가 발생합니다. 그렇지 않으면 치명적인 오류가 발생합니다. <br><br>
함수를 호출하여 객체를 호출할 때의 응답 메서드입니다.
<?php 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('Clone is not allowed error: ' . E_USER_ERROR); } } $a = Singleton::getInstance(); $b = Singleton::getInstance(); if( $a === $b ){ echo 'equal<br>'; } $c = clone $b; ?>
boolean true
boolean false
__set_state()
이 정적 메서드는 클래스를 내보내기 위해 var_export()가 호출될 때 호출됩니다.