博客列表 >5.28容器注入(IOC)和门面模式(facade)

5.28容器注入(IOC)和门面模式(facade)

李洋
李洋原创
2018年05月29日 22:54:17750浏览
  • 容器:也称服务容器,简称(IOC),

  • 基本思想:就是拿来就用,最大限度的简化外部对象的调用,类似于:[即插即用]的思想。

  • 简单的讲就是将工具类打包成一个容器,在客户端完成工具类的实例化为对象,再以参数的方式直接传递给工作类的方法

  • 基本实现分三步:

        首先是工具类

        //数据库操作类
        class Db
        {
           //数据库连接
           public function connect()
           {
              return '数据库连接成功<br>';
           }
        }
        
        //数据验证类
        class Validate
        {
           //数据验证
           public function check()
           {
              return '数据验证成功<br>';
           }
        }
        
        //视图图
        class View
        {
           //内容输出
           public function display()
           {
              return '用户登录成功';
           }
        }


    1.创建容器,将类与类的实例化过程绑定到容器中(不局限于类,也可是接口或其它)

    //一.创建容器类        
        class Container
        {
           //创建属性,用空数组初始化,该属性用来保存类与类的实例化方法
           protected $instance = [];
        
           //初始化实例数组,将需要实例化的类,与实例化的方法进行绑定
           public function bind($abstract, Closure $process)
           {
              //键名为类名,值为实例化的方法
              $this->instance[$abstract] = $process;
           }
        
           //创建类实例
           public function make($abstract, $params=[])
           {
              return call_user_func_array($this->instance[$abstract],[]);
           }
        
        }

2.服务注册,将可能用到的工具类全部绑定到容器中

//二、服务绑定: 将类实例注册到容器中        
        $container = new Container(); 
        
        //将Db类绑定到容器中
        $container->bind('db', function(){
           return new Db();
        });
        
        //将Validate类实例绑定到容器中
        $container->bind('validate', function(){
           return new Validate();
        });
        
        //将View类实例绑定到容器中
        $container->bind('view', function(){
           return new View();
        });
        
        //测试:查看一下当前容器中的类实例
        // var_dump($container->instance); die;

3.容器依赖:或者叫依赖容器,调用工作类时直接传入容器对象即可,工具类的实例化由容器完成

//三、容器依赖:将容器对象,以参数的方式注入到当前工作类中        
        
        //用户类:工作类
        class User
        {
           //创建三个成员属性,用来保存本类所依赖的对象
           // protected $db = null;
           // protected $validate = null;
           // protected $view = '';
           //这三个与外部对象对应的三个属性可以全部删除了,因为它们都已经事先注册到了容器中
        
           //用户登录操作
           // public function login(Db $db, Validate $validate, View $view)
           //此时,只需从外部注入一个容器对象即可,Db,Validate和View实例方法全部封装到了容器中
           public function login(Container $container)
           {
              //实例化Db类并调用connect()连接数据库
              // $db = new Db();
              // echo $db->connect();
              echo $container->make('db')->connect();
        
              //实例化Validate类并调用check()进行数据验证
              // $validate = new Validate();
              // echo $validate->check();
              echo $container->make('validate')->check();
        
              //实例化视图类并调用display()显示运行结果
              // $view = new View();
              echo $container->make('view')->display();
           }
        }
        //在客户端完成工具类的实例化(即工具类实例化前移)
        // $db = new Db();
        // $validate = new Validate();
        // $view = new View();
        
        //现在注入过程就非常简单了,只需要从外部注入一个容器对象即可
        
        //创建User类
        $user = new User();
        
        //调用User对象的login方法进行登录操作
        // echo $user->login();
        // 将该类依赖的外部对象以参数方式注入到当前方法中,当然,推荐以构造器方式注入最方便
        echo '<h3>用依赖容器进行解藕:</h3>';
        // echo $user->login($db, $validate, $view);
        //现在工作类中的login方法不需要再像对象依赖注入那样写三个对象了,只需要一个容器对象就可以了
        echo $user->login($container);
  • 外观模式:facade,也叫门面模式 也叫静态代理
    1.用一句来说:就是将操作进行封装,对外提供一个统一的接口(使用了facade类  当你调用类中的方法时,不在考虑该方法是否为静态,统统使用静态方式调用即可)


  • require 'container.php';
    
    //创建Facade类,实现以上三个功能
    class Facade
    {
       //连接数据库
       public static function connect(Container $container)
       {
          return $container->make('db')->connect();
       }
    
       //用户数据验证
       public static function check(Container $container)
       {
          return $container->make('validate')->check();
       }
    
       //输出提示信息
       public static function display(Container $container)
       {
          return $container->make('view')->display();
       }
    }
    
    //客户端调用
    echo Facade::connect($container);
    echo Facade::check($container);
    echo Facade::display($container);
  • 可以在外观模型中使用初始化方法事先注入容器对象,来简化客户端调用
  • require 'container.php';
    
    
    class Facade
    {
       //创建成员属性保存容器对象
       protected static $container = null;
    
       //创建初始化方法为容器对象赋值
       public static function initialize(Container $container)
       {
          static::$container = $container;
       }
       //连接数据库
       public static function connect()
       {
          return static::$container->make('db')->connect();
       }
    
       //用户数据验证
       public static function check()
       {
          return static::$container->make('validate')->check();
       }
    
       //输出提示信息
       public static function display()
       {
          return static::$container->make('view')->display();
       }
    }
  • //客户端调用
    
    //初始化类门面类中的容器对象
    Facade::initialize($container);
    
    //静态统一调用内部的方法(无须重复注入依赖容器对象啦,实现了细节隐藏,通用性更强)
    echo Facade::connect();
    echo Facade::check();
    echo Facade::display();


声明:本文内容转载自脚本之家,由网友自发贡献,版权归原作者所有,如您发现涉嫌抄袭侵权,请联系admin@php.cn 核实处理。
全部评论
文明上网理性发言,请遵守新闻评论服务协议