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

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

控制反转(Inversion of Control)

就是当一个对象需要依赖于另一个对象时,通常由调用对象来创建被调用对象的实例。在Spring中,创建被调用对象的工作不再由调用对象来完成,而由Spring 容器来完成,然后注入调用对象,这就是Spring的控制反转IOC。(IOC是一种设计模式 )

依赖注入(Dependency Injection)

是目Q最优秀的解耦方式。使用依赖注入时,J2EE应用中的各种组件不需要以硬编码方式耦合在一起,当某个java实例需要其它java实例时,系统会自动提供需要的实例,无需程序显示获取. (DI是一种具体实现方式 )
依赖注入,是spring 的核心机制,可以使Spring 的bean 以配置文件组织在一起,而不是硬编码的方式耦合在一起。

Spring 控制反转和依赖注入是一个意思,不同的叫法,简单的说就是你需要的对象不需要你自己创建了,而是Spring给你创建好以后注入进去。Spring的依赖注入对调用对象和被调对象几乎没有任何要求,完全支持POJO之间的依赖关系的管理。依赖注入通常的两种方式是设值注入和构造注入。

(01)设置注入

设置注入是指通过setter方法传入被调用者的实例。这种注入方式简单、直观。设置注入也称set注入,即在程序中给每个变量都增加一个set方法,用来设置属性的值。So…上实例

这里定义接口

package com.ym.dao.imple;
public interface IAnimal {
	/**
	 * 定一个到招呼的方法: 
	 */
	public void animalWay1();
}

next:
还是定义一个接口

package com.ym.dao.imple;

public interface ICallType {
	/**
	 * 定一个到叫声的方法: 
	 */
	void call();

}

next:
这里定一个 DCallType 实现类继承 ICallType 接口

package com.ym.dao;
import com.ym.dao.imple.ICallType;
public class DCallType implements ICallType {
	@Override
	public void call() {
		System.out.println("hellow !!!  我是一只小猫 ,喵喵叫....");
	}
}

next:
这里定一个 DAnimal 实现类继承 IAnimal 接口

package com.ym.dao;

import com.ym.dao.imple.IAnimal;
import com.ym.dao.imple.ICallType;
import com.ym.entity.Animal;


public class DAnimal implements IAnimal {

	//定义一个ICallType 接口参数
	private ICallType call;
	//get方法
	public ICallType getCall() {
		return call;
	}
	//set方法
	public void setCall(ICallType call) {
		this.call = call;
	}
	//默认构造函qi
	public DAnimal() {
	}

	//接口实现方法
	@Override
	public void animalWay1() {
		//调用叫声方法
		call.call();
	}
}

next:
applicationContext.xml中配置这样写的

	<bean id="animal011"  class="com.ym.dao.DAnimal" > 	
		<property name="call">
				<ref bean="dCallType"/>
		</property>
	</bean>
	<bean id="dCallType"	class="com.ym.dao.DCallType" />

Last:
我们来测试一哈

public void animalTest02(){	
		//通过配置文件获得Spring容器
		ApplicationContext ac=new ClassPathXmlApplicationContext("applicationContext.xml");
		//获得接口 IAnimal
		IAnimal ianimal1=(IAnimal)ac.getBean("animal011");
		ianimal1.animalWay1();
	}

结果:
在这里插入图片描述

So, as you can see from the above:

配置文件里bean的class元素中不能是接口,而必须是真正的实现类。
另外,Spring会自动接管每个bean定义里的property元素定义。Spring会在执行无参数的构造器后,创建默认的bean实例,并调用对应的setter方法为程序注入属性值。这里 property 定义的属性值将不再由该bean来主动创建和管理,而是接受Spring的注入
每个bean的id属性是该bean的唯一标识,程序通过id属性来访问bean,bean与bean的依赖关系也通过id属性关联。

(02)构造注入

指通过构造函数来完成依赖关系的设定,而不是通过setter方法。

对qing面的 DAnimal 类简单修改哈:

public class DAnimal implements IAnimal {

	//定义一个ICallType 接口参数
	private ICallType call;
	
	//这里说明哈:此时方式下就不需要setCall方法了
	
	//默认构造函qi
	public DAnimal() {
	}
	
	//构造注入需要的带参数的构造qi
	public DAnimal(ICallType call) {
		super();
		this.call = call;
	}

	//接口实现方法
	@Override
	public void animalWay1() {
		//调用叫声方法
		call.call();
	}
}

next:
applicationContext.xml中配置这样写的

<bean id="dCallType"	class="com.ym.dao.DCallType" />
	<!--depends-on="call" 表示在 animal01的bean 初始化qing先必须qiang制初始化call 这个、bean的实例 --> 
<bean id="animal01"  class="com.ym.dao.DAnimal" depends-on="dCallType"> 	
	<!-- 给类中接口赋值 必须有有参构造函数 -->
	<constructor-arg>
		<ref bean="dCallType"/>
	</constructor-arg>
</bean>

Last:
测试同上测试方法一样

From the above point of view:

两种注入方式效果是一样的,区别在于创建DAnimal 实例中 ICallType 属性的时候不同而已。
设值注入是先创建一个默认的bean实例,然后调用对应的setter方法注入依赖关系;
构造注入则在创建bean实例时,已经完成了依赖关系的注入。

然后看哈两个注入方式的比较

(01)设值注入的优点:
a、设值注入与传统的javaBean的写法更相似,so 对于我们来说更容易理解and 通过setter方法设定依赖关系显得更加直观、自然。
b、对于复杂的依赖关系,如果采用构造注入,就会导致构造qi过于臃肿。
c、在某些属性可选的时候,多参数的构造qi更加笨重。
(02)设值注入的优点:
a、可以在构造qi中决定依赖关系的注入顺序,eg:组件中qi它依赖关系的注入,常常需要依赖于Datasource的注入。采用构造注入 时,可以在代码中qing 晰的决定注入顺序,优先依赖的优先注入。
b、对于依赖关系无需变化的bean。构造注入更有用处。因为没有setter方法,所有的依赖关系quan部在构造qi内设定,因此无须担心后续代码对依赖关系产生破换。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值