IoC控制反转与DI依赖注入

IoC: Inversion of Control

IoC是一种模式。目的是达到程序的复用。下面的两篇论文是对IoC的权威解释:

一个对IoC形象化的描述,出自论文 http://www.digibarn.com/friends/curbow/star/XDEPaper.pdf 中的:

Don‘t call us, we’ll call you (Hollywood’s Law).
A tool should arrange for Tajo to notify it when
the user wishes to communicate some event to
the tool, rather than adopt an “ask the user for
a command and execute it” model.

当用户(人、程序)要使用一个工具的时候,让框架来激活这个工具,而不是让用户执行一些命令来激活它。

即,原则是,使用组件的地方,只需要知道要使用什么样的组件,它会来自某个地方,但不需要知道组件具体是谁。

按照这个原则开发的系统,实现了各组件之间相互依赖的解耦。即替换某个组件,不需要修改使用这个组件的组件。

在编程语言实现上,IoC所涉及的工作主要有:

  • 定义接口、虚类等规范约束。这是基础。
  • 开发具体的实现规范的组件。
  • 开发组件创建工厂。具体包括组件配置、组件创建等。
  • 开发组件管理器。具体包括缓存组件对象、将组件交给需要它的对象等。

IoC有很多具体的实现模式:

(1)Dependency Injection (DI) 依赖注入

组件管理器将组件注入到使用组件的对象中。

  • 构造函数方式注入。被注入的对象在构造器中传入。
  • 设值方法注入。通过setter方法注入。
  • 接口方法注入。需要被注入的类实现一个具体的接口,由一个注入器调用这个接口方法,完成组件注入。
// Java示例:接口方法注入
 
// 注入依赖的接口
public interface InjectFinder {
void injectFinder(MovieFinder finder);
}
 
// 注入依赖的接口
public interface InjectFinderFilename {
void injectFilename(String filename);
}
 
// 注入器接口
public interface Injector {
public void inject(Object target);
}
 
// ==
 
// 仅为InjectFinder组件
class MovieLister implements InjectFinder {
public void injectFinder(MovieFinder finder) {
this.finder = finder;
}
}
 
// 既是InjectFinderFilename组件,又是InjectFinder接口的注入器
class ColonMovieFinder implements Injector, InjectFinderFilename {
public void injectFilename(String filename) {
this.filename = filename;
}
 
public void inject(Object target) {
((InjectFinder) target).injectFinder(this);
}
}
 
// 仅为InjectFinderFilename接口的注入器
class FinderFilenameInjector implements Injector {
public void inject(Object target) {
((InjectFinderFilename)target).injectFilename("movies1.txt");
}
}
 
// ==
 
class Tester {
 
private Container container;
 
private void configureContainer() {
container = new Container();
// 注册组件。完成创建组件。
registerComponents();
// 注册注入器。完成组件注入。
registerInjectors();
container.start();
}
 
private void registerComponents() {
// 这里模式是 组件名 - 组件
container.registerComponent("MovieLister", MovieLister.class);
container.registerComponent("MovieFinder", ColonMovieFinder.class);
}
 
private void registerInjectors() {
// 这里的模式是 注入接口 - 注入器
// 容器会遍历所有的组件,如果组件实现了注入接口,将调用对应的注入器,将这个组件作为参数,传递给注入器
container.registerInjector(InjectFinder.class, container.lookup("MovieFinder"));
container.registerInjector(InjectFinderFilename.class, new FinderFilenameInjector());
}
 
public static void main(String[] args) {
configureContainer();
MovieLister lister = (MovieLister)container.lookup("MovieLister");
Movie[] movies = lister.moviesDirectedBy("Sergio Leone");
assertEquals("Once Upon a Time in the West", movies[0].getTitle());
}
 
}

(2)Service Locator 服务定位器

组件管理器将组件交给一个全局的服务者。组件的使用者主动向这个全局的服务者索取需要的组件。

参考

本文链接:http://www.cnblogs.com/afarmer/p/4259133.html

IoC控制反转与DI依赖注入的更多相关文章

  1. 谈谈php里的IOC控制反转,DI依赖注入

    理论 发现问题 在深入细节之前,需要确保我们理解"IOC控制反转"和"DI依赖注入"是什么,能够解决什么问题,这些在维基百科中有非常清晰的说明. 控制反转(In ...

  2. [转帖]什么是IOC(控制反转)、DI(依赖注入)

    什么是IOC(控制反转).DI(依赖注入) 2018-08-22 21:29:13 Ming339456 阅读数 20642   原文地址(摘要了部分内容):https://blog.csdn.net ...

  3. Spring的三大核心思想:IOC(控制反转),DI(依赖注入),AOP(面向切面编程)

    Spring核心思想,IoC与DI详解(如果还不明白,放弃java吧) 1.IoC是什么?    IoC(Inversion of Control)控制反转,IoC是一种新的Java编程模式,目前很多 ...

  4. 谈谈php里的IOC控制反转,DI依赖注入(转)

    转自:http://www.cnblogs.com/qq120848369/p/6129483.html 发现问题 在深入细节之前,需要确保我们理解"IOC控制反转"和" ...

  5. Spring-初识Spring框架-IOC控制反转(DI依赖注入)

    ---恢复内容开始--- IOC :控制反转 (DI:依赖注入)使用ioc模式开发 实体类必须有无参构造方法1.搭建Spring环境下载jarhttp://maven.springframework. ...

  6. 学习Spring IOC控制反转和DI依赖注入总结

    30岁的小曹,20岁的身体,还在坚持在能力允许控制范围内22点睡觉,5点起床锻炼身体,好好学习,除了加班或者像今天这样的深夜,再一次写已经有X百万人写过的 spring Ioc 的总结博客. 一.IO ...

  7. 三大框架 之 Spring(IOC控制反转、DI依赖注入)

    目录 常用词汇 left join与left outer join的区别 Struts2的标签库导入 Spring Spring概述 什么是Spring spring特点 下载 IOC 什么IOC 传 ...

  8. spring(一) IOC 控制反转 、DI 依赖注入

    IOC 控制反转:创建对象的方式  变成了由Spring来主导 IOC底层原理:对象工厂 1.导入jar包:4个核心jar和1个依赖jar spring-beans-4.3.9.RELEASE.jar ...

  9. .net 温故知新:【7】IOC控制反转,DI依赖注入

    IOC控制反转 大部分应用程序都是这样编写的:编译时依赖关系顺着运行时执行的方向流动,从而生成一个直接依赖项关系图. 也就是说,如果类 A 调用类 B 的方法,类 B 调用 C 类的方法,则在编译时, ...

随机推荐

  1. 关于eclipse android 在manifest改app应用包名注意事项

    在我刚学android 时候,然后立即就做项目.那时连eclipse 使用都不是很熟练.很多功能都不知道.新手如果这时去改app应用的包名,没有改好会变成所有控件在R文件里面id都找不到. 先上两张图 ...

  2. Leetcode 27 Remove Element STL

    和remove zero类似的方法完成该题 class Solution { public: int removeElement(vector<int>& nums, int va ...

  3. How Tomcat works — 七、tomcat发布webapp

    目录 什么叫发布 webapp发布方式 reload 总结 什么叫发布 发布就是让tomcat知道我们的程序在哪里,并根据我们的配置创建Context,进行初始化.启动,如下: 程序所在的位置 创建C ...

  4. [推荐]Zookeeper大型分布式系统的可靠协调系统知识介绍

    [推荐]Zookeeper大型分布式系统的可靠协调系统知识介绍 基于Zookeeper的锁开发手册 http://wenku.baidu.com/view/acbb8fc6102de2bd960588 ...

  5. 如何设计优秀的API(转)

    到目前为止,已经负责API接近两年了,这两年中发现现有的API存在的问题越来越多,但很多API一旦发布后就不再能修改了,即时升级和维护是必须的.一旦API发生变化,就可能对相关的调用者带来巨大的代价, ...

  6. 闲暇时间开发的个人app

    最近一段时间公司不是很忙,晚上基本没怎么加班.所以自己利用晚上在家的时间开发了一个app(奇趣营),其实自从转android开发以来,就有想过要自己开发一个app.一方面可以提升自己的经验:另一方面可 ...

  7. [C/C++] zltabout(带缩进的格式化输出)v1.0。能以相同的代码绑定到 C FILE 或 C++流

    作者:zyl910 一.缘由 在写一些生成文本的程序时,经常需要使用带缩进的格式化输出的功能.以前为此写过不少类似的函数,可惜它们的可重用性很差. 这是因为——1) C语言的FILE*不支持重定向到自 ...

  8. Hadoop学习篇 2 初识 Hadoop

    在一个全配置的集群上,运行Hadoop意味着在网络分布的不同服务器上运行一组守护进程 (daemons),这些守护进程或运行在单个服务器上,或运行与多个服务器上,他们包括: (1) NameNode( ...

  9. find the peak value

    A peak element is an element that is greater than its neighbors. Given an input array where num[i] ≠ ...

  10. EntityFramework 5.0 CodeFirst 教程04-查询,插入,更新,和删除数据

    ---------------------目录-------------------------- EntityFramework 5.0 CodeFirst 教程04-查询,插入,更新,和删除数据  ...