php之魔术方法 __set() __get() __isset() __unset() __call() __callStatic() __invoke() __toString()

__set()与__get()

当一个类里面,属性被设置为私有属性时,这个属性是不能在外部被访问的。那么当我们又想在外部访问时该怎么办呢,我们可以用方法来实现。举例如下:

 1 class Test
 2 {
 3     private $abc;
 4 
 5     public function setAbc($val)
 6     {
 7         $this->abc=$val;
 8     }
 9 
10     public function getAbc()
11     {
12         return $this->abc;
13     }
14 }
15 
16 $test=new Test();
17 $test->setAbc("this is abc!");
18 var_dump($test->getAbc());

以上这个代码就可以实现在外部访问私有属性,但是如果我们的私有属性不只一个时,假如还有一个ABD,那么我们要外部访问的话,还需要再写一个专门针对ABD的方法,这样就显得很麻烦了。如何实现多个私有属性访问,而又不用一个个去写方法呢?这时候 __set跟__get就派上用场了。上面的代码就可以这样写了,举例如下:

 1 class Test
 2 {
 3     private $abc;
 4     private $abd;
 5 
 6     public function __set($var, $val)
 7     {
 8         $this->$var=$val;
 9     }
10 
11     public function __get($var)
12     {
13         return $this->$var;
14     }
15 }
16 
17 $test=new Test();
18 $test->abc="this is private abc";
19 echo $test->abc;

__set($var,$val):有两个参数,第一个是属性名,第二个是属性值。

__get($var):只有一个参数,属性名。

以上这段代码中,当我们给私有属性赋值时,它就会自动去执行__set()这个方法,同样的,当我们要获取属性值时,它也会自动去执__get()这个方法。访问的语法跟访问公有属性语法一样。

__isset()

__isset($var):是用来检测私有属性是否存在。只有一个参数,属性名。我们用代码来举例说明,如下:

1 class Test
2 {
3     private $abc='abc';
4 }
5 $test=new Test();
6 var_dump(isset($test->abc));

上面这段代执行的结果是返回布尔FALSE,虽然类里面有abc这个属性,但是它是私有属性,是不能被外部所访问的,所以返回布尔FALSE。如果要测试,我们可以在类里面加上__isset()方法,举例如下:

 1 class Test
 2 {
 3     private $abc='abc';
 4 
 5     public function __isset($var)
 6     {
 7         return isset($this->$var)?true:false;
 8     }
 9 }
10 $test=new Test();
11 var_dump(isset($test->abc));

上面这段代码执行的结果是返回布尔TRUE,当外部的isset($test->abc) 检测不到abc时,它就会自动去执行类里面的__isset()这个方法,然后返回结果。

__unset()

__unset($var):用来删除私有属性,只有一个参数,属性名。举例如下:

 1 class Test
 2 {
 3     private $abc='abc';
 4 
 5     public function __unset($var)
 6     {
 7         echo "__unset:".$var;
 8         unset($this->$var);
 9     }
10 }
11 $test=new Test();
12 unset($test->abc);

上面这段代码中,当外部的unset($test->abc)检测不到abc时,就会去执行类里面的__unset()这个方法,然后删除属性。

 

__call()   __callstatic()

__call($func,$arguments):为了避免调用的方法不存在而出错,我们可以用这个魔术方法__call()来实现。这个魔术方法有两个参数,一个是你调用的方法名:func,一个是你调用的方法里面的参数:arguments。

__callstatic($func,$arguments):为了避免调用的静态方法不存上而出错,我们就可以用这个魔术方法来实现,跟__call()是一样的,只不过一个是公有方法,一个有私有方法。现用代码举例如下:

 1 class Test
 2 {
 3     public function __call($func,$arguments)
 4     {
 5         echo "$func";
 6         print_r($arguments);
 7     }
 8 }
 9 
10 $test= new Test();
11 $test->go(1,2);

这段代码返回的结果是,调用的方法名:go。go方法所带的参数:1跟2,不过这个是以数组的形式存储的,不管所带的参数是一个还是两个都是以数组存储的。我们在类里面是没有定义go这个方法的,所以当我们在外部调用时,发现没有go这个方法时,就会自动去执行类里面的__call()。

 1 class Test
 2 {
 3     public static function __callStatic($func,$arguments)
 4     {
 5         echo "$func";
 6         print_r($arguments);
 7     }
 8 }
 9 
10 Test::go(1,2);

上面这段代码返回的结果跟__call()的示例代码是一样的,只不过代码不一样,一个不是static方法,一个是static方法,外部调用的语法也不一样。static过之后,就表示这个方法是属于类的,而不是属于对像的。

 

__invoke()

__invoke($arg):当一个对象以函数的形式被调用时,就用自动去执行__invoke()这个方法。举例代码如下:

class Test
{
    public function __invoke($arg)
    {
        echo "$arg";
    }
}

$test= new Test();
$test("this is class,but as method!");

 

__toString()

__toString():当一个对像被打印时,就会去调用这个魔术方法。这个魔术方法是没有参数的。方法内要返回一个结果。举例代码如下:

class Test
{
    public function __toString()
    {
        return "echo class";
    }
}

$test= new Test();
echo $test;

 

 

posted @ 2019-12-07 23:50  白小白学IT  阅读(148)  评论(0)    收藏  举报