Spring IoC容器
Spring IoC容器:
BeanFactory和ApplicationContext
BeanFactory
- BeanFactory 就是一个管理 Bean 的工厂,它主要负责初始化各种 Bean,并调用它们的生命周期方法。
ApplicationContext
- ApplicationContext 是 BeanFactory 的子接口,也被称为应用上下文。
ApplicationContext 接口有两个常用的实现类
1)ClassPathXmlApplicationContext
该类从类路径 ClassPath 中寻找指定的 XML 配置文件,找到并装载完成 ApplicationContext 的实例化工作
ApplicationContext applicationContext = new ClassPathXmlApplicationContext(String configLocation);
configLocation 参数用于指定 Spring 配置文件的名称和位置,如 applicationContext.xml。
2)FileSystemXmlApplicationContext
该类从指定的文件系统路径中寻找指定的 XML 配置文件,找到并装载完成 ApplicationContext 的实例化工作
ApplicationContext applicationContext = new FileSystemXmlApplicationContext(String configLocation);
它与 ClassPathXmlApplicationContext 的区别是:在读取 Spring 的配置文件时,FileSystemXmlApplicationContext 不再从类路径中读取配置文件,而是通过参数指定配置文件的位置,它可以获取类路径之外的资源,如“F:/workspaces/applicationContext.xml”。
注意的是,BeanFactory 和 ApplicationContext 都是通过 XML 配置文件加载 Bean 的。
二者的主要区别:
如果 Bean 的某一个属性没有注入,则使用 BeanFacotry 加载后,在第一次调用 getBean() 方法时会抛出异常,而 ApplicationContext 则在初始化时自检,这样有利于检查所依赖的属性是否注入。
Spring DI(依赖注入)的实现方式
- 属性注入和构造注入
控制反转:
当某个 Java实例需要另一个 Java 实例时,传统的方法是由调用者创建被调用者的实例(例如,使用 new 关键字获得被调用者实例),而使用 Spring框架后,被调用者的实例不再由调用者创建,而是由 Spring 容器创建
依赖注入:
Spring 容器在创建被调用者的实例时,会自动将调用者需要的对象实例注入给调用者,这样,调用者通过 Spring 容器获得被调用者实例
两种实现方式:
1)属性 setter 注入
指 IoC 容器使用 setter 方法注入被依赖的实例。通过调用无参构造器或无参 static 工厂方法实例化 bean 后,调用该 bean 的 setter 方法,即可实现基于 setter 的 DI。
2)构造方法注入
指 IoC 容器使用构造方法注入被依赖的实例。基于构造器的 DI 通过调用带参数的构造方法实现,每个参数代表一个依赖。
Spring中Bean的作用域
- singleton 和 prototype 两种最常用的作用域
singleton 作用域
singleton 是 Spring 容器默认的作用域,当一个 Bean 的作用域为 singleton 时,Spring 容器中只会存在一个共享的 Bean 实例,并且所有对 Bean 的请求,只要 id 与该 Bean 定义相匹配,就只会返回 Bean 的同一个实例。
通常情况下,这种单例模式对于无会话状态的 Bean(如 DAO 层、Service 层)来说,是最理想的选择。
在 Spring 配置文件中,可以使用 元素的 scope 属性,将 Bean 的作用域定义成 singleton
<bean id="person" class="com.mengma.scope.Person" scope="singleton"/>
prototype 作用域
使用 prototype 作用域的 Bean 会在每次请求该 Bean 时都会创建一个新的 Bean 实例。因此对需要保持会话状态的 Bean(如 Struts2 的 Action 类)应该使用 prototype 作用域。
在 Spring 配置文件中,要将 Bean 定义为 prototype 作用域,只需将 元素的 scope 属性值定义成 prototype
<bean id="person" class="com.mengma.scope.Person" scope="prototype"/>
primary:主要的,当一个抽象类拥有多个子类的时候,可以指定一个主要的类作为子类,创建对象时,优先使用该对象
parent:可以继承其他配置
*部分属性不被继承:abstract,autowire
depends-on:我可以不依赖该Bean,跟给属性没有任何关系,但是SpringIOC容器中必须要有该Bean
scope:bean的作用域
^singelton:单例
prototype:非单例
- autowire:自动注入
byName:根据属性的名称注入
byType:根据属性的类型进行注入
引入外部属性文件 <context:property-placeholder location="mysqldb.properties"/> location:属性文件的位置及名称 访问属性文件中的内容 ${key} SpEL:Spring中的表达式 #{表达式} 支持程序运行时查询和操作对象的表达式语言,类似于EL,可以为Bean动态赋值 功能 可以直接通过ID/NAME访问bean对象 可以访问Bean对象中的属性 可以调用Bean对象中的方法 可以进行运算 算数运算 + - * / % ^(次方) 关系运算 >(gt) >=(ge) <(lt) <=(le) ==(eq) !=(ne) 逻辑运算 &&(and) ||(or) !(not) 条件运算 ?: 连接 + 可以进行正则表达式匹配 被匹配的内容 matches 正则表达式'
Bean的生命周期
在SpringIOC容器中,对象从创建到销毁的全过程
*可以在生命周期的过程中的某些特定时刻执行某些特定行为
生命周期
调用构造方法创建对象
postProcessBeforeInitialization
*初始化方法
postProcessAfterInitialization
使用Bean
*销毁方法
Bean的后置处理器(创建所有的Bean的时候都会执行改后置处理中的方法)
1、创建后置处理器类
2、实现BeanPostProcessor接口
3、重写
postProcessBeforeInitialization:初始化执行之前执行
postProcessAfterInitialization:初始化执行之后执行