Spring IOC(DI)之注入方式
一次被问到IOC的注入方式,当时脑袋一阵混乱,不知道噻。于是google了一下,发现众说纷纭,有说三种的,有说四种的。都滚犊子吧,还是看看官方文档吧。
DI exists in two major variants, Constructor-based dependency injection and Setter-based dependency injection.
从官方文档上也看不出到底有几种注入方式,从上面这段引文中仅仅能知道主要有两种:构造器注入方式和Setter注入方式。
构造器注入方式
构造器注入方式是通过Spring容器调用含参构造函数实现的,每个参数都相当于一个依赖。这种方式和把参数传递给工厂方法来构造bean是非常相似的。
构造器参数解析
构造器通过参数类型匹配,如果参数类型都很明确,在bean实例化时,通过参数顺序来选择合适的构造函数。示例如下:
package x.y;
public class Foo {
public Foo(Bar bar, Baz baz) {
// ...
}
}
不存在参数类型不确定性是指Bar和Baz不在一个继承体系内(除Object体系外),因此在配置<constructor-arg/>时,不需要特别指定参数的索引值或类型。如下:
<beans>
<bean id="foo" class="x.y.Foo">
<constructor-arg ref="bar"/>
<constructor-arg ref="baz"/>
</bean>
<bean id="bar" class="x.y.Bar"/>
<bean id="baz" class="x.y.Baz"/>
</beans>
就像上面例子中那样,当被其他bean引用时,就已经可以确定类型了。但是构造器参数中使用了像这样<value>true<value>的基本数据类型,在没有提示的前提下Spring是没办法确定类型的,就像下面这个例子:
package examples;
public class ExampleBean {
// No. of years to the calculate the Ultimate Answer
private int years;
// The Answer to Life, the Universe, and Everything
private String ultimateAnswer;
public ExampleBean(int years, String ultimateAnswer) {
this.years = years;
this.ultimateAnswer = ultimateAnswer;
}
}
参数类型匹配构造器
使用简单类型作为参数时,指定type属性值,这样Spring容器就可以通过类型匹配来选择合适的构造器。这样上面那个问题就可以这样解决:
<bean id="exampleBean" class="examples.ExampleBean">
<constructor-arg type="int" value="7500000"/>
<constructor-arg type="java.lang.String" value="42"/>
</bean>
构造器参数索引值
根据构造器中参数的索引值来指定index属性值来匹配参数。如下:
<bean id="exampleBean" class="examples.ExampleBean">
<constructor-arg index="0" value="7500000"/>
<constructor-arg index="1" value="42"/>
</bean>
指定索引值就可以解决一个构造器使用两个相同类型参数的问题。注意索引值是从0开始的。
构造器参数名称
从Spring3.0起,可以使用构造器参数名称来消除参数模糊问题。
<bean id="exampleBean" class="examples.ExampleBean">
<constructor-arg name="years" value="7500000"/>
<constructor-arg name="ultimateanswer" value="42"/>
</bean>
需要特殊说明的是:如果要使用参数名称,那么需要在编译的时候启用debug标志,这样Spring才能用构造器中找到参数名称。如果不能或者不想开启debug模式,可以使用@ConstructorProperties注解来指定构造器中参数的名称。示例如下:
package examples;
public class ExampleBean {
// Fields omitted
@ConstructorProperties({"years", "ultimateAnswer"})
public ExampleBean(int years, String ultimateAnswer) {
this.years = years;
this.ultimateAnswer = ultimateAnswer;
}
}
Setter注入方式
基于Setter的注入方式是在Spring容器调用无參构造器或者无參静态工厂方法后,再调用bean中的setter方法实现的。
下面这个例子是一个通过纯setter方式注入的例子,这种方式在Java中非常常见,就是一个POJO,不依赖任何与容器相关的接口、类、注解。
public class SimpleMovieLister {
// the SimpleMovieLister has a dependency on the MovieFinder
private MovieFinder movieFinder;
// a setter method so that the Spring container can 'inject' a MovieFinder
public void setMovieFinder(MovieFinder movieFinder) {
this.movieFinder = movieFinder;
}
// business logic that actually 'uses' the injected MovieFinder is omitted...
}
依赖解析过程
Spring容器是这样解析依赖的:
Spring容器通过配置元数据创建和初始化
ApplicationContext,配置元数据可以使用Xml,Java代码或者注解描述。每个bean的依赖形式都是由属性,构造器参数,静态工厂方法的参数(如果使用静态工厂方法替代构造器)来表述的,当bean被实例化的时候,提供给这个bean。
每个属性或者构造器的参数的值都需要去设置,或者是容器中某一bean的引用。
每个属性或构造器的参数的值都是从一种形式转换为属性或参数实际的类型。Spring默认可以将String类型转换为所有内置类型。比如
int,long,String,boolean等。
Spring IOC(DI)之注入方式的更多相关文章
- spring ioc三种注入方式
spring ioc三种注入方式 IOC ,全称 (Inverse Of Control) ,中文意思为:控制反转 什么是控制反转? 控制反转是一种将组件依赖关系的创建和管理置于程序外部的技术. 由容 ...
- Spring IOC三种注入方式(接口注入、setter注入、构造器注入)(摘抄)
IOC ,全称 (Inverse Of Control) ,中文意思为:控制反转, Spring 框架的核心基于控制反转原理. 什么是控制反转?控制反转是一种将组件依赖关系的创建和管理置于程序外部的技 ...
- Spring IOC 三种注入方式
1. 接口注入 2. setter注入 3. 构造器注入 对象与对象之间的关系可以简单的理解为对象之间的依赖关系:A类需要B类的一个实例来进行某些操作,比如在A类的方法中需要调用B类 ...
- Spring IOC 三种注入方式(构造器,setter,接口)
Spring的依赖注入有三种方式: 1,构造器注入 2,setter注入 3,接口注入 下面我给大家介绍一下这三种注入 1.构造器注入 构造器注入主要是依赖于构造方法去实现,构造方法可以是有参也可以是 ...
- 关于Spring IOC (DI-依赖注入)需要知道的一切
关联文章: 关于Spring IOC (DI-依赖注入)你需要知道的一切 关于 Spring AOP (AspectJ) 你该知晓的一切 <Spring入门经典>这本书无论对于初学者或者有 ...
- 关于Spring IOC (DI-依赖注入)
<Spring入门经典>这本书无论对于初学者或者有经验的工程师还是很值一看的,最近花了点时间回顾了Spring的内容,在此顺带记录一下,本篇主要与spring IOC相关 ,这篇博文适合初 ...
- 关于Spring IOC (DI-依赖注入)你需要知道的一切
<Spring入门经典>这本书无论对于初学者或者有经验的工程师还是很值一看的,最近花了点时间回顾了Spring的内容,在此顺带记录一下,本篇主要与spring IOC相关 ,这篇博文适合初 ...
- AutoFac IoC DI 依赖注入
AutoFac IoC DI 依赖注入 记录点点滴滴知识,为了更好的服务后来者! 一.为什么使用AutoFac? 之前介绍了Unity和Ninject两个IOC容器,但是发现园子里用AutoFac的貌 ...
- spring四种依赖注入方式(转)
spring四种依赖注入方式!! 平常的java开发中,程序员在某个类中需要依赖其它类的方法,则通常是new一个依赖类再调用类实例的方法,这种开发存在的问题是new的类实例不好统一管理,spring提 ...
随机推荐
- Shot(三分)
Shot Time Limit: 5000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
- linux内核源码阅读之facebook硬盘加速利器flashcache
从来没有写过源码阅读,这种感觉越来越强烈,虽然劣于文笔,但还是下定决心认真写一回. 源代码下载请参见上一篇flashcache之我见 http://blog.csdn.net/liumangxiong ...
- IOS开发新手教程(一)-数据类型和运算符
OC语法入门(一) 数据类型和运算符 1.1凝视 凝视和其它语言一样,同意单行 ,多行凝视,一份规范的代码里面须要有一些正式的凝视,例如以下凝视: /* 这是多行 凝视 */ //这是多行凝视 OC语 ...
- linux下内存调试工具——valgrind
1.valgrind之memcheck 最常用的工具,用来检测程序中出现的内存问题,所有对内存的读写都会被检测到,一切对malloc()/free()/new/delete的调用都会被捕获.所以,它 ...
- C#中的虚方法和抽象方法(Thirteenth Day)
今天在云和学院学了很多,我这次只能先总结一下C#中的虚方法和抽象的运用. 理论: 虚方法: •用virtual修饰的方法叫做虚方法 •虚方法可以在子类中通过override关键字来重写 •常见的虚方法 ...
- codeforces 478B Random Teams
codeforces 478B Random Teams 解题报告 题目链接:cm.hust.edu.cn/vjudge/contest/view.action?cid=88890#probl ...
- OD调试篇1—Hello
OD调试篇1—Hello 要求:通过OD将程序的标题“I love fishc.com”改为“I love you” 一.找到程序的标题“I love fishc.com” 1.把程序拖到OD运行出现 ...
- uva 11077 置换
/** 给定一个置换,看能不能存在一个置换A^2 = B 思路; 循环节长度为偶数n的置换只能由循环节长度为长度2*n 的置换A*A 而变得.所以只需求出循环节,看循环节长度为偶数的个数是否为偶数个即 ...
- selenium 怎么处理display:none
页面HTML是这样的: .... <div class="cf w index-middle"> <div id="li" class=&q ...
- C#调用Java方法
C#调用Java方法(详细实例) 阅读目录 C#调用c++ C#调用JAVA方法 C#可以直接引用C++的DLL和转换JAVA写好的程序.最近由于工作原因接触这方面比较多,根据实际需求,我们通过一个具 ...