您的位置:首页 > 其它

依赖注入与控制反转的理解

2015-08-09 21:54 429 查看

定义

控制反转(IoC/Inverse of Control): 调用者不再创建被调用者的实例,而是由spring框架实现(容器创建)所以称为控制反转。

依赖注入(DI/Dependency injection): 容器创建好实例后再注入到调用者称为依赖注入。

当某个角色(调用者)需要另外一个角色(被调用者)的协助时,在传统的程序设计过程中,通常由调用者创建被调用者的实例。如果创建被调用者实例的工作不再由调用者来完成,而是由外部容器完成,因此称为控制反转;创建调用者的工作通常由外部容器完成,然后注入到调用者,因此成为依赖注入。

图例表示过程

没有IoC/DI的时候,常规的A使用C类的示意图:



有了IoC/DI容器之后,A类不再主动创建C类了,如图:



而是被动等待,等待IoC/DI的容器获取一个C的实例,然后反向注入到A类中去,如图:



代码实例

定义一个接口

[code]public abstract class Person{
    abstract void sayHello();
}

第一个实现类

[code]public class Chinese extends Person{
    public void sayHello(){
        System.out.println("您好!");
    }
}

第二个实现类

[code]public class American extends Person{
    public void sayHello(){
        System.out.println("Hello,nice to see you!");
    }
}

调用的类,与传统的类的区别:该类调用Person子类的方法,传统设计在本类中创建实例,而在此类中并没有创建实例。

[code]public class User{
    Person p=null;
    public Person getPerson(){
        return p;
    }
    //提供给容器的注入方法是setter,容器通过setter将Person类的实例(Person子类的实例化对象)注入到User类中
    public void setPerson(Person p){
        this.p = p;
    }

    //调用Person子类重写的sayHello方法,这里的p并没有实例化
    public void function(){
        p.sayHello();
    }

}

外部‘容器’

[code]public class Container{
    public static User getUser(){
        //实例化被调用的对象,也就是上图的C类
        Person p = new Chinese();
        User user = new User();
        //容器类Container通过setter向调用者User注入Person Chinese的实例
        user.setPerson(p);
        return user;
    }
}

测试类

[code]public class Test{
    public static void main(String[] args){
        User user = Container.getUser();
        user.function(); //后台输入“您好!”
    }
}

总结

根据上述,可以看出,依赖注入和控制反转是对同一件事情的不同描述,从某个方面来讲,就是描述的角度不同。

依赖注入是从应用程序的角度在描述,可以把依赖注入描述地完整点:应用程序依赖容器创建并注入它所需要的外部资源。

控制反转是从容器的角度在描述,可以把控制反转描述地完整点:由容器反向地向应用程序注入应用程序所需要的外部资源。

参考资料:

控制反转与以来注入

控制反转(IoC)和依赖注入(DI)简介
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: