首页 > 代码库 > 关于PHP魔术方法__call的一点小发现

关于PHP魔术方法__call的一点小发现

  好久没有上博客园写文章了,今晚终于有点空了,就来写一下昨天的一点小发现。

  我自己所知,C++,Java的面向对象都有多态的特点,而PHP没有,但PHP可以通过继承链方法的重写来实现多态的属性。而魔术方法会在特定情况下被触发,我们也可以对其进行重写。

---------------------------------------------------------------------------------------------------------摘抄开始------------------------------------------------------------------------------------------------------

  以下摘自5idev.com:

__call()(Method overloading)

为了避免当调用的方法不存在时产生错误,可以使用 __call() 方法来避免。该方法在调用的方法不存在时会自动调用,程序仍会继续执行下去。

1 function __call(string $function_name, array $arguments)
2 {
3     ......
4 }

该方法有两个参数,第一个参数 $function_name 会自动接收不存在的方法名,第二个 $args 则以数组的方式接收不存在方法的多个参数。

---------------------------------------------------------------------------------------------------------摘抄结束------------------------------------------------------------------------------------------------------

  利用这一个特性,以及PHP的函数call_user_func_array,可以达到类似在控制器内用当前对象调用非继承链里的方法的效果,而我想调用的redis的方法(因为$this比$this->redis多打好多字呢。。。而且think PHP里面的缓存拓展使用起来也很麻烦(lll¬ω¬)  )

  下面贴一下代码:

 1 <?php
 2 namespace Home\Controller;
 3 use Think\Controller;
 4 class BaseController extends Controller {
 5 
 6     protected $redis = null;
 7     /**
 8      * [__construct description]
 9      * 实例化redis
10      */
11     public function __construct(){
12         if (!$this->redis) {
13             $this->redis = new \Home\Controller\RedisController();
14         }
15         parent::__construct();
16     }
17 
18     /**
19      * 重写方法重载方便使用redis
20      * @param  string $method_name 重载的方法名
21      * @param  array $args        参数
22      * @return mixed              返回结果
23      */
24     public function __call($method_name, $args){
25         if (method_exists($this->redis, $method_name)) {
26             return call_user_func_array(array($this->redis, $method_name), $args);
27         }
28         parent::__call();
29     }
30 }

  写完之后,真的觉得自己分外风骚!不过因为是在think PHP3.2.3框架里面做的,get方法不能调用redis的(但其实可以把redis或者controller类里面的方法改名)虽然不知道这样做会不会有什么隐患或者问题,但我觉得这样做还是很方便的,以后有其他的类,还可以加进去。

  如果代码有什么不足或者错误,请各位指正~谢谢~

关于PHP魔术方法__call的一点小发现