控制反转(IoC)和依赖注入(Dependency Injection)实例分析讲解

知道91 | 教程 | 2016-05-19 | 阅读:7411

当初在学习java的时候,经常看到IOC容器注入这个词,特别是在讲Spring框架的时候提到的最多,但是就是不明白控制反转(IoC)是什么意思,或者似懂非懂,总是模模糊糊的,经过多年的学习,然后回过头来总结,才逐渐明白控制反转(IoC)是什么意思。

控制反转(IOC)和依赖注入

一个概念首先从名字上最能说明他的意思。控制反转,可以分解就是“控制”+“反转”。控制指对对象的引用的控制,想象一下面向过程编程的时候,如果A对象要使用B(本文称之为资源对象),按照顺向思维应该怎么做呢,肯定是当A对象用到B的时候去创建B对象,这里是说A控制B,A对象是主动去获取B,这种情况称之为正向。现在是“反转”就是需要反过来,A对象不是主动去获取B,而是被动的等待,等待IOC的容器(你可以理解为提供被调用对象的框架,比如Spring)去获取B的一个实例,注入到A的对象中去,由于这个过程和原来的顺向过程刚好反过来了,所以称之为反向。

控制反转(IoC)有一个很形象的比喻称之为“好莱坞原则”,好莱坞原则是什么呢?不出名的演员想要演戏,然后就会去找导演啊,导演不认识你,你就死缠烂打,导演就说:“你不要打电话来了,我们会打给你的”,导演就说IOC的容器,演员就是A对象,它需要角色颜色,这里的角色就是导演(IOC容器)提供的。

什么是依赖注入(Dependency Injection)

说完了控制反转,在说说什么是依赖注入。有了控制反转的概念才有依赖注入。前面讲了,控制反转是需要需要IOC容器主动提供资源对象给调用者,怎么提供呢?当然是IOC容器给A对象注入,因为A对象依赖IOC容器,所以这种叫依赖注入。

依赖注入一般有3种方法:

  • 构造函数注入
  • 设置值注入
  • 接口注入

下面使用代码分析一下这三种注入方法。

构造函数注入

 public class A
    {
        private B b;
        public A(B b)
        {
            this.b = b;
        }

        public void MyBusiness()
        {
            b.DoSomething();
        }
    }

    public class B
    {
        public void DoSomething()
        {

        }
    }

如代码所示,B是通过参数传入A类中。

设置值注入

    public class A
    {
        private B b;

        public void SetB(B b)
        {
            this.b = b;
        }

        public void MyBusiness()
        {
            b.DoSomething();
        }
    }

    public class B
    {
        public void DoSomething()
        {

        }
    }

稍微修改了一下上面的代码,B是通过A的方法来设置的。

接口注入

    public interface IA
    {
        void CreateB(B b);
    }

    public class A:IA
    {
        private B b;

        public void CreateB(B b)
        {
            this.b = b;
        }

        public void MyBusiness()
        {
            b.DoSomething();
        }
    }

    public class B
    {
        public void DoSomething()
        {

        }
    }

如代码所示,IA这个接口抽象了创建B对象的方法,A实现接口IA就必须实现创建B的方法,这样也实现接口注入。

通过上面的讲解你应该明白所谓控制反转和依赖注入,参加的角色无非就是三个,对象A(资源调用者)、对象B(被调用的资源)、ioC容器(创建对象B并传入给A)。整体把握这个要点,那么控制反转(IOC)和依赖注入(ID)的整个精髓你就领悟到了。