(转) Spring读书笔记-----Spring的Bean之配置依赖

时间:2022-06-08 07:25:31

前一篇博客介绍了Spring中的Bean的基本概念和作用域(Spring读书笔记-----Spring的Bean之Bean的基本概念),现在介绍Spring Bean的基本配置。

从开始我们知道Java应用中各组件的相互调用的实质可以归纳为依赖关系。根据注入方式的不同,Bean的依赖注入可以分为两种形式:

1、  属性:通过<property …/>元素配置,对应设置注入。

2、  构造器参数:通过<constructor-arg…/>元素配置,对应构造注入。

不管是属性,还是构造器参数,都视为Bean的依赖,接受Spring容器管理,依赖关系的值要么是一个确定的值,要么是Spring容器中的其他Bean的引用。

在一般情况下,我是不应该在配置文件中管理普通属性的引用,通常只是用配置文件管理容器中的Bean实例的依赖关系。

Spring在实例化容器时,会校验BeanFactory中每一个Bean的配置。这些校验包括:

Bean引用的依赖Bean是否指向一个合法的Bean。

Bean的普通属性值是否获得一个有效值。

对于singleton作用域的Bean,如果没有强行取消其预初始化的行为,系统会在创建Spring容器时预初始化所用singleton Bean,与此同时,该Bean所依赖的Bean也被一起实例化。

BeanFactory与ApplicationContext实例化容器中的Bean的时机也是不同的:BeanFactory等到程序需要Bean实例时才创建Bean,而ApplicationContext是在创建ApplicationContext实例时,会预初始化容器中的全部Bean。同时在创建BeanFactory时不会立即创建Bean实例,所以有可能程序可以正确地创建BeanFactory实例,但是当请求Bean实例时依然抛出一个异常:创建Bean实例或注入它的依赖关系时出现错误。所以当配置错误的延迟出现,会给系统带来一些不安全的因素。而ApplicationContext则是默认预初始化所有singleton作用域的Bean,所以ApplicationContext实例化过程比BeanFactory实例化过程的时间和内存开销大,但是一旦创建成功,应用后面的响应速度会非常快,同时可以检验出配置错误,故一般都是推荐使用ApplicationContext作为Spring容器。

其实我们可以指定lazy-int=”true”来强制取消singleton作用域的Bean的预初始。这样该Bean就不会随着ApplicationContext启动而预实例化了。

Spring可以为任何java对象注入任何类型的属性,只要改java对象为该属性提供了对应的setter方法即可。

  1. <bean id="person" class="lee.Person">
  2. <!-- Property配置需要依赖注入的属性 -->
  3. <property name="name" value="chenming" />
  4. <property name="age" value="22" />
  5. </bean>
	<bean id="person" class="lee.Person">
<!-- Property配置需要依赖注入的属性 -->
<property name="name" value="chenming" />
<property name="age" value="22" />
</bean>

Spring会为<bean…/>元素创建一个java对象,一个这样的java对象对应一个Bean实例,对于如上代码,Spring会采用如下形式来创建Java实例。

  1. //获取lee.Person类的Class对象
  2. Class  personClass = Class.forName("lee.Person");
  3. //创建lee.Person类的默认实例
  4. Object personBean = personBean.newInStance();
	//获取lee.Person类的Class对象
Class personClass = Class.forName("lee.Person");
//创建lee.Person类的默认实例
Object personBean = personBean.newInStance();

创建该实例后,Spring就会遍历该<bean../>元素的所有<property…/>子元素。<bean…/>元素每包含一个<property…/>子元素,Spring就会为该Bean实例调用一次setter方法。类似于下面程序:

  1. //获取name属性的setter方法
  2. String setName = "set"+"Name";
  3. //获取lee.Person类里面的Set()Name方法
  4. java.lang.reflect.Method setMethod = personClass.getMethod(setName, aVal.getClass());
  5. //调用Bean实例的SetName()方法
  6. setMethod.invoke(personBean, aVal);
	//获取name属性的setter方法
String setName = "set"+"Name";
//获取lee.Person类里面的Set()Name方法
java.lang.reflect.Method setMethod = personClass.getMethod(setName, aVal.getClass());
//调用Bean实例的SetName()方法
setMethod.invoke(personBean, aVal);

对于使用<constructor-arg…/>元素来指定构造器注入,Spring不会采用默认的构造器来创建Bean实例,而是使用特定的构造器来创建该Bean实例。

  1. <bean id="person" class="lee.Person">
  2. <constructor-arg index="0" value="aVal" />
  3. <constructor-arg index="1" value="bVal" />
  4. </bean>
	<bean id="person" class="lee.Person">
<constructor-arg index="0" value="aVal" />
<constructor-arg index="1" value="bVal" />
</bean>

针对上面的代码,Spring会采用类似如下的代码来创建Bean实例:

  1. //获取lee.Person类的class对象
  2. Class  personClass = Class.forName("lee.Person");
  3. //获取第一个参数是aVal类型,第二个参数是bVal类型的构造器
  4. Constructor personCtr = personClass.getConstructor(aVal.getClass(),bVal.getClass());
  5. //以指定构造器创建Bean实例
  6. Object bean = personCtr.newInstance(aVal,bVal);
	//获取lee.Person类的class对象
Class personClass = Class.forName("lee.Person");
//获取第一个参数是aVal类型,第二个参数是bVal类型的构造器
Constructor personCtr = personClass.getConstructor(aVal.getClass(),bVal.getClass());
//以指定构造器创建Bean实例
Object bean = personCtr.newInstance(aVal,bVal);

上面的程序只是一个实例,实际上Spring还需要根据<property…/>元素、<contructor-arg../>元素所使用value属性,ref属性等来判断需要注入的到底是什么数据类型,并要对这些值进行合适的类型转换,所以Spring的实际处理过程会更加复杂。

读李刚《轻量级Java EE企业应用实战》

(转) Spring读书笔记-----Spring的Bean之配置依赖的更多相关文章

  1. Spring读书笔记-----Spring的Bean之Bean的基本概念

    从前面我们知道Spring其实就是一个大型的工厂,而Spring容器中的Bean就是该工厂的产品.对于Spring容器能够生产那些产品,则取决于配置文件中配置. 对于我们而言,我们使用Spring框架 ...

  2. Spring读书笔记-----Spring的Bean之设置Bean值

    [java] view plaincopyprint? Java实例的属性值可以有很多种数据类型.基本类型值.字符串类型.java实例甚至其他的Bean实例.java集合.数组等.所以Spring允许 ...

  3. (转)Spring读书笔记-----Spring的Bean之Bean的基本概念

    从前面我们知道Spring其实就是一个大型的工厂,而Spring容器中的Bean就是该工厂的产品.对于Spring容器能够生产那些产品,则取决于配置文件中配置. 对于我们而言,我们使用Spring框架 ...

  4. &lpar;转&rpar;Spring读书笔记-----Spring核心机制:依赖注入

    Java应用(从applets的小范围到全套n层服务端企业应用)是一种典型的依赖型应用,它就是由一些互相适当地协作的对象构成的.因此,我们说这些对象间存在依赖关系.加入A组件调用了B组件的方法,我们就 ...

  5. Spring读书笔记-----Spring核心机制:依赖注入

    spring框架为我们提供了三种注入方式,分别是set注入,构造方法注入,接口注入.今天就和大家一起来学习一下 依赖注入的基本概念 依赖注入(Dependecy Injection),也称为IoC(I ...

  6. Spring 学习笔记(四)—— XML配置依赖注入

    依赖注入(DI)与控制反转(IoC)是同一个概念,都是为了处理对象间的依赖关系. 通过DI/IoC容器,相互依赖的对象由容器负责创建和装配,而不是在代码中完成. Spring支持通过setter方法和 ...

  7. Spring读书笔记——bean解析

    前情回顾 上篇<Spring读书笔记--bean加载>我们从代码角度介绍了有哪些类负责解析XML文件,又是如何一步步从XML格式脱变成我们熟悉的bean的,直到DefaultBeanDef ...

  8. Spring读书笔记——bean创建(上)

    通过<Spring读书笔记--bean加载>和<Spring读书笔记--bean解析>,我们明白了两件事. Spring如何加载消化一个xml配置文件 Spring如何将xml ...

  9. Spring读书笔记——bean创建(下)

    有关Spring加载bean系列,今天这是最后一篇了,主要接上篇对于从Spring容器中获取Bean的一些细节实现的补充. <Spring读书笔记--bean加载>--Spring如何加载 ...

随机推荐

  1. ie6的兼容总结

    ie6的兼容处理总结 1.透明背景图: .timer { _filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='my.png ...

  2. pdb文件部分解释

    pdb文件包含了编译后程序指向源代码的位置信息,用于调试的时候定位到源代码,主要是用来方便调试的. 在程序发布为release模式时,建议将 pdb文件删除, 同时,对外发布的时候,也把 pdb删除, ...

  3. C&num; 根据IP查询地址归属地

    必备文件:IPLocation.dll.QQWry.Dat 下载地址:http://pan.baidu.com/s/1jG1dlOy (可百度下载) 之前有过将 QQWry.Dat 转为 Access ...

  4. IO多路复用

    1.事件驱动模型 上一篇写的协程仅仅是切换,本身不能实现并发,什么时候切换也不知道 那么什么时候切回去呢?怎么确定IO操作完了?通过回调函数  对于事件驱动型程序模型,它的流程大致如下: 开始---& ...

  5. wap2app(九)-- 使用mui&period;previewImage之后,页面a链接不能跳转

    使用Hbuilder的长按保存图片的预览图片之后,页面所有的a链接都不能跳转. 解决办法: 可以使用下面绑定tap利用js跳转,亲测有效. mui('body').on( 'tap' , 'a' , ...

  6. &lbrack;原&rsqb;Jenkins&lpar;十四&rpar;---jenkins示例:admin管理所有项目,新建用户只能看部分项目

    /** * lihaibo * 文章内容都是根据自己工作情况实践得出. *如有错误,请指正 * 版权声明:本博客欢迎转发,但请保留原作者信息! http://www.cnblogs.com/horiz ...

  7. MongoDB 2&period;6配置副本集,支持端口号修改和用户登录认证

    mongoDB系列之(二):mongoDB 副本集 Mongodb2.6副本集验证部署和认证 副本集有以下特点: 1. 最小构成是:primary,secondary,arbiter,一般部署是:pr ...

  8. 【LOJ】 &num;2545&period; 「JXOI2018」守卫

    题解 只会蠢蠢的\(n^3\)--菜啊-- 我们发现最右的端点一定会选,看到的点一定是当前能看到的斜率最小的点变得更小一点,记录下这个点,在我们遇到一个看不到的点的时候,然后只用考虑R到它斜率最小的这 ...

  9. 接口测试基础——第6篇unittest模块(一)

    我们先来简单介绍一下unittest框架,先上代码,跟住了哦~~ 1.建立如下结构的文件夹: 注意,上面的文件夹都是package,也就是说你在new新建文件夹的时候不要选directory,而是要选 ...

  10. how to remove untagged &sol; none images

    docker rmi $(docker images -a| grep "^<none>" | awk '{print $"3"}')