BeanFactory和ApplicationContext的区别
概念: BeanFactory是Spring框架中IoC容器的顶层接口,它只是用来定义一些基础功能,定义一些基础规范,而<br>ApplicationContext是它的一个子接口,所以ApplicationContext是具备BeanFactory提供的全部功能<br>的。<br>
通常我们称BeanFactory为SpringIOC的基础容器,ApplicationContext是容器的高级接口,比<br>BeanFactory要拥有更多的功能,⽐如说国际化⽀持和资源访问(xml,java配置类)等等<br>
BeanFactory的类图
启动IoC容器的方式
Java环境下启动Ioc容器
ClassPathXmlApplicationContext:从类的根路径下加载配置文件(推荐使用)
FileSystemXmlApplicationContext:从磁盘路径上加载配置文件
AnnotationConfigApplicationContext:纯注解模式下启动Spring容器
Web环境下启动IoC容器
从xml启动容器
<web-app><br> <display-name>Archetype Created Web Application</display-name><br> <br> <!-- 配置Spring ioc容器的配置文件--><br> <context-param><br> <param-name>contextConfigLocation</param-name><br> <param-name>classpath:applicationContext.xml</param-name><br> </context-param><br> <!--使用监听器启动Spring ioc容器--><br> <listener><br> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class><br> </listener><br></web-app>
Servlet中代码实现
从配置类启动容器
<web-app><br><br> <display-name>Archetype Created Web Application</display-name><br><br> <!--配置让contextloaderContext知道我们是使用的注解启动ioc容器--><br> <context-param><br> <param-name>contextClass</param-name><br> <param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value><br> </context-param><br><br> <!-- 配置启动类的全限定类名--><br> <context-param><br> <param-name>contextConfigLocation</param-name><br> <param-value>com.lvqz.spring.config.SpringConfig</param-name><br> </context-param><br><br> <!--使用监听器启动Spring ioc容器--><br> <listener><br> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class><br> </listener><br></web-app>
xml配置中基础知识
实例化Bean的三种方式
使用无参构造函数
在默认情况下,它会通过反射调⽤⽆参构造函数来创建对象。如果类中没有⽆参构造函数,将创建<br>失败。
使用静态方法构造
在实际开发中,我们使⽤的对象有些时候并不是直接通过构造函数就可以创建出来的,它可能在创<br>建的过程 中会做很多额外的操作。此时会提供⼀个创建对象的⽅法,恰好这个⽅法是static修饰的<br>⽅法,即是此种情 况。
使用实例方法构造
此种⽅式和上⾯静态⽅法创建其实类似,区别是⽤于获取对象的⽅法不再是static修饰的了,⽽是<br>类中的⼀ 个普通⽅法。此种⽅式⽐静态⽅法创建的使⽤⼏率要⾼⼀些。<br><br>在早期开发的项⽬中,⼯⼚类中的⽅法有可能是静态的,也有可能是⾮静态⽅法,当是⾮静态⽅法<br>时,即可 采⽤下⾯的配置⽅式:
生命周期
singleton:单例模式
对象出生:当创建容器时,对象就被创建了
对象或者:只要容器在,对象一直活着
对象死亡:当销毁容器时,对象就被销毁了。
一句话总结:单例模式的bean对象生命周期与容器相同。
prototype:多例模式
对象出生:当适用对象时,创建新的对象实例
对象活着:只要对象在使用中,就一直活着
对象死亡:当对象长时间不用时,被java的垃圾回收器回收了
一句话总结:多例模式的bean对象,spring框架值负责创建爱你,不负责销毁。
自己不大使用的几个bean属性
factory-bean属性:用于指定创建当前bean对象的工厂bean的唯一标识。<font color="#fdb813">当指定了此属性之后,class属性失效。</font>
factory-method属性:用于指定创建当前bean对象的工厂方法,<font color="#fdb813">如配合factory-bean属性使用,则class属性失效。如配合class属性使用,则方法必须是static的。</font>
init-method:用于指定bean对象的初始化方法,此方法会在bean对象装配后调用。<font color="#fdb813">必须是一个无参方法</font>。
destory-method:用于指定bean对象的销毁方法,<font color="#fdb813">此方法会在bean对象销毁前执行。它只能为scope是singleton时起作用。</font>
DI依赖注入配置
按照注入的方式分类
构造函数注入
顾名思义,就是利⽤带参构造函数实现对类成员的数据赋值。
set方法注入
它是通过类成员的set⽅法实现数据的注⼊。(使⽤最多的)
按照注入的数据类型分类
基本类型和String
其他Bean类型
复杂类型(集合类型)
Array,List,Set,Map,Properties中的一种类型
SpringIOC的高级特性
lazy-init延迟加载
概念:ApplicationContext 容器的默认⾏为是在启动服务器时将所有 singleton bean 提前进行实例化。提前实例化意味着作为初始化过程的⼀部分,ApplicationContext 实例会创建并配置所有的singleton bean。
属性使用和设置:lazy-init="false",立即加载,表示在spring启动时,立刻进行实例化。<br>如果不想让某个singleton bean 在 ApplicationContext实现初始化时被提前实例化,那么可以将bean设置为延迟实例化。
<b><font color="#99ccff">当一个立即加载的bean依赖了一个延迟加载的bean时:</font></b><br><br>设置 lazy-init 为 true 的 bean 将不会在 ApplicationContext 启动时提前被实例化,而是第一次向容器通过 getBean 索取 bean 时实例化的。<br><br>如果一个设置了立即加载的 bean1,引用了一个延迟加载的 bean2 ,那么 bean1 在容器启动时被实例化,而 bean2 由于被 bean1 引用,所以也被实例化,这种情况也符合延时加载的 bean 在第一次调用时才被实例化的规则。
如果一个 bean 的 scope 属性为 scope="pototype" 时,即使设置了 lazy-init="false",容器启动时也不会实例化bean,而是调用 getBean()方法实例化的。
FactoryBean和BeanFactory
BeanFactory:BeanFactory接口是容器的顶级接口,定义了容器的一些基础行为,负责生产和管理Bean的一个工厂,具体使用它下面的子接口类型,例如ApplicationContext;此处我们重点分析FactoryBean
Factory:<br>Spring中Bean有两种,一种是普通Bean,一种是工厂Bean(FactoryBean),FactoryBean可以生成某一个类型的Bean实例(返回给我们),也就是说我们可以借助于它自定义Bean的创建过程。<br><br>Bean创建的三种方式中的静态方法和实例化方法和FactoryBean作用类似,FactoryBean使用较多,尤其在Spring框架一些组件中会使用,还有其他框架和Spring框架整合时使用<br>
在配置中,想要获取Factory下返回的对象,getBean(工厂Id);<br>想要或者工厂对象 getBean(&工厂Id);
后置处理器
BeanPostProcessor
使用场景:在Bean对象实例化(<font color="#fdb813">并不是Bean的整个生命周期完成</font>)之后可以使用BeanPostProcessor进行后置处理做一些事情
实现BeanPostProcessor后要实现的两个方法
postProcessBeforeInitialization
postProcessAfterInitialization
BeanFactoryPostProcessor
使用场景:<br>工厂初始化(BeanFactory) ->Bean对象<br>在BeanFactory初始化之后可以使⽤BeanFactoryPostProcessor进行后置处理做一些事情<br>
BeanFactory级别的处理,是针对整个Bean的工厂进行处理,典型应<br>用:PropertyPlaceholderConfigurer
此接口只提供了一个方法,方法参数为ConfigurableListableBeanFactory,该参数类型定义了一些方法
其中有个方法名为getBeanDefinition的⽅法,我们可以根据此方法,找到我们定义bean 的BeanDefinition对象。然后我们可以对定义的属性进行修改,以下是BeanDefinition中的方法
<b>BeanDefinition对象</b>:我们在 XML 中定义的 bean标签,Spring 解析 bean 标签成为⼀个 JavaBean,这个JavaBean 就是 BeanDefinition
注意:调用BeanFactoryPostProcessor方法时,这时候bean还没有实例化,此时 bean 刚被解析成BeanDefinition对象
关于SpringBean的生命周期的一些其他接口
BeanNameAware
BeanFactoryAware
ApplicationContextAware
InitlalizingBean
init-method
在初始化方法和销毁方法中的执行顺序:注解>接口>配置<br>例如:初始化方法 @PostContruct>InitializingBean>配置属性init-method