Spring

8/13

传统JavaBean和Spring中的Bean的区别:

1.用处不通:传统的JavaBean通常只是作为数值传递的载体;Spring中的Bean可以是任何组件

2.结构不通:传统JavaBean需要为每个变量提供get/set方法;Spring中的Bean只需要为设置注入的变量提供set方法

3.生命周期不通:传统JavaBean不接受任何容器管理其生命周期;Spring中的Bean由Spring容器管理其生命周期


Spring如何将XML配置文件中的Bean放入自己的容器(Spring如何通过反射机制来获取Bean):

首先在XML配置文件中,一个bean标签包含两个元素:id(唯一标示),class(完整类名,不能是接口或者抽象类,必须是实现类)。之后Spring读取这两个元素的值,简化为如下

代码将该bean添加到容器中:

//id元素

String id = ....

//class元素

String className = ....

//反射获取Class

Class clazz = Class.forName(className);

//利用Class无参构造器生产Bean实例

Object obj = class.newInstance();

//加入到Spring容器中

container.put(id,obj)


依赖注入的方式:设值注入和构造注入

如果Spring管理的Bean包含一些私有属性,那么在Spring初始化该Bean实例的时候,会通过以上两种方式为其注入属性值。也就是说Spring生成的Bean实例是完整的,包含

属性参数的。

1.设值注入:IOC容器使用Bean中的SET方法来为其注入被依赖的对象

在XML配置文件中,如果bean标签下含有property子标签,说明该Bean类包含一些属性,在初始化Bean对象时,会根据property标签中的子元素来判断该属性所属的类型

<bean ...>

//value子元素说明该属性是基本数据类型或其封装类或者String等类型

<property name="属性名" value="..."/>

//ref子元素说明该属性是其他bean类型

<property name="属性名" ref="其他bean id"/>

<bean/>

使用设值注入一定要在该Bean中提供需要注入属性的set方法

//定义一个主bean

<bean id ="person" class="....service.Person">

//该主bean依赖一个id为axe的bean

<property name="axe" ref="axe"/>

</bean>

//被依赖的axe bean

<bean id="axe" class="....service.Axe"/>

这时在主bean Person中包含一个Axe类型的属性,我们要利用Spring容器为它注入值以完成整个Person的实例化过程。

Public class Person{

//变量名axe应该与property中的name一致

private Axe axe;

//提供set方法帮助Spring完成设置注入,注意方法名一定要是小写"set" + 大写变量首字母后的变量名 "Axe"

public void setAxe(Axe a){

this.axe = a;

}

}

Spring在调用默认构造器实例化该Bean之后,立即调用对应的set方法为Bean的属性注入相应类型的值,注入的代码也是通过反射原理实现的:

String proName = axe;

String proClass = ....service.Axe;

String setName = "set" + proName.substring(0,1).toUpperCase() + proName.substring(1); //setAxe

Object paramBean = container.get(proName);//获取Axe实例

//获取方法名为setAxe,方法形参类型为Axe的set方法

Method setter = clazz.getMethod(setName ,paramBean.getClass());

//反射执行person的setAxe方法

setter.invoke(obj,paramBean );


2.构造注入:IOC容器使用构造器来注入被依赖对象

构造注入不需要像设值注入一样提供set方法,但却需要提供带参数的构造方法;换句话说,设值注入是在Spring底层通过无参构造器生产Bean实例,然后调用set方法注入属

性,而构造注入则是Spring在底层通过反射执行带参构造器对Bean进行实例化,构造实例的同时为其注入属性。构造注入需要提供<constructor-arg...>子标签

//定义一个主bean

<bean id ="person" class="....service.Person">

//该person拥有一个参数类型为Axe的构造方法,也可以使用value元素,代表常用类型,并且可以指定type 例如:<constructor-arg value="123" type="in"/>

<constructor-arg ref="axe"/>

//可以有多个constructor-arg标签,代表调用多个参数的构造方法,标签具有前后顺序,第一个标签对应第一个参数

<....>

</bean>

//被依赖的axe bean

<bean id="axe" class="....service.Axe"/>

Public class Person{

private Axe axe;

//使用构造注入必须提供一个与<constructor-arg>标签列表相符的构造方法

public Person(Axe a){

this.axe = a

}

}

与之前反射生成bean实例放入容器中类似:

//id元素

String id = ....//person

//class元素 //....service.Person

String className = ....

//反射获取Class

Class clazz = Class.forName(className);

//利用Class带参构造器生产Bean实例

 Constructor c=clazz.getDeclaredConstructor(Class.forName(....service.Axe));

Object obj = c.newInstance(axe)

//加入到Spring容器中

container.put(id,obj)


理解依赖注入:

A对象需要调用B对象的方法,这种情形Spring称之为以来,即A对象以来B对象,传统方式往往调用者主动创建被调用对象,然后再调用被依赖对象的方法这种硬编码方式,或

者通过工厂模式获得被依赖对象。这两种方法或多或少都增加了代码的耦合度。而Spring通过容器管理所有Bean,并在Bean类初始化对象时为其注入相应的属性值,极大程度

上对代码进行了解耦。

依赖注入:Spring容器将被依赖对象赋值给调用者,相当于为调用者注入依赖的实例的这种方式叫做依赖注入

控制反转:调用者无需主动去创建或获取被依赖对象,调用者只需要被动的接受Spring容器注入的依赖实例。调用者从原先的主动获取到现在的被动接受的这种方式称为控制反


8/14

Spring容器有两个核心借口:BeanFactory和ApplicationContext,其中ApplicationContext是前者的子接口,BeanFactory接口含有以下几个方法:

判断Spring容器是否包含该id为name的Bean实例 boolean containsBean(String name)对应xml中bean的id

获取Spring容器中id为name的Bean的class类型 Class<?> getType(String name) 对应xml中bean的id

获取Spring容器中属于requiredType类型的唯一的Bean实例 <T> T getBean(Class<T> requiredType)对应xml中bean的class

获取Spring容器中id为name的Bean实例 Object getBean(String name)对应xml中bean的id

获取Spring容器中id为name,类型为requiredType的Bean实例 <T> T getBean(String name ,Class<T> requiredType) 对应xml中bean的id,class


ApplicationContext对BeanFactory的增强:

容器初始化时,默认初始化所有singleton Bean

可利用如ContextLoader的支持类,在web应用中自动创建ApplicationContext,而不需要手动创建它


ApplicationContext事件机制:

Spring容器中继承了ApplicationEvent类的Bean被称为容器事件

Spring容器中实现了ApplicationListener接口的Bean被称为监听器,实现该接口必须实现以下方法

onApplicationEvent(ApplicationEvent event):当容器中发生任何事件时,此方法都将触发



8/17

之前都是论述Spring容器如何将xml配置文件中的Bean放入容器中,假设现在有一个Bean,需要获取自己当前所在的Spring容器作为自己的参数(属性),来实现类似国际

化、发布事件等功能(该类事件需要用Spring 容器来实现).Bean获取当前管理自己的Spirng容器需要实现ApplicationContextAware接口,并定义一个私有的容器属性,该接

口包含一个setApplicationContext(ApplicationContext ctx)接口,当Spring容器检测所有Bean的时候,一旦发现某些Bean实现了ApplicationContextAware接口,就会将自己作

为参数传给该Bean的实例对象中的容器变量,例子如下:

pubic class Person implement ApplicationContextAware{

private ApplicationContext ctx;

public void setApplicationContext(ApplicationContext ctx){

this.ctx = ctx;

}

}


xml配置Bean的一些参数详解:





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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值