Spring 的核心功能就是提供一個(gè) IoC 容器后控,用于管理應(yīng)用程序中的 bean禾锤,在容器中配置元數(shù)據(jù)來(lái)管理 Bean 之間的依賴關(guān)系膏燃,Java 程序中的類都可以交由 Spring 容器管理削樊。
一滥搭、Bean 管理
1. 元數(shù)據(jù)
配置 Spring 元數(shù)據(jù)的方式有三種:
- 基于 XML 方式配置
- 基于注解方式配置
- 基于 Java 方式配置
Spring 最早的時(shí)候提供BeanFactory
接口實(shí)現(xiàn) Bean 容器酸纲,而后面新增的許多功能都是基于其子接口ApplicationContext
來(lái)實(shí)現(xiàn)的,前面說(shuō)的三種配置方式瑟匆,可以使用下面三個(gè)實(shí)現(xiàn)類來(lái)實(shí)例化容器闽坡。
|interface BeanFactory (org.springframework.beans.factory)
|---interface ApplicationContext (org.springframework.context)
|---|---class FileSystemXmlApplicationContext (org.springframework.context.support)
|---|---class ClassPathXmlApplicationContext (org.springframework.context.support)
|---|---class AnnotationConfigApplicationContext (org.springframework.context.annotation)
例如使用 ClassPathXmlApplicationContext
來(lái)通過(guò) classpath
目錄下的配置文件實(shí)例化容器:
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("bean.xml");
2. Bean 實(shí)例化
在 Spring 容器中配置好的 Bean 都會(huì)被 Spring 自動(dòng)實(shí)例化,以供在開(kāi)發(fā)過(guò)程中注入直接可以使用愁溜,而不需要手動(dòng)去 new
對(duì)象疾嗅。
2.1 構(gòu)造器實(shí)例化
Spring 容器默認(rèn)使用類的無(wú)參構(gòu)造器來(lái)實(shí)例化 Bean,也可以指定其他帶參數(shù)的構(gòu)造器來(lái)實(shí)例化冕象。
<!--默認(rèn)使用無(wú)參構(gòu)造器-->
<bean id="beanProvider" class="cn.codeartist.spring.bean.xml.BeanProvider"/>
<!--使用其他構(gòu)造器-->
<bean id="beanExample" class="cn.codeartist.spring.bean.xml.BeanExample">
<constructor-arg index="0" value="碼匠公眾號(hào)"/>
<constructor-arg index="1" value="2021"/>
<constructor-arg index="2" ref="beanProvider"/>
</bean>
2.2 靜態(tài)工廠方式實(shí)例化
Spring 容器支持使用靜態(tài)工廠方法來(lái)實(shí)例化 Bean,在類中定義一個(gè) static
方法來(lái)創(chuàng)建對(duì)象實(shí)例。
public class BeanExample {
private static BeanExample beanExample = new BeanExample();
public static BeanExample getInstance() {
return beanExample;
}
}
在 Bean 配置中使用 factory-method
屬性來(lái)指定工廠方法晒杈。
<bean id="beanExample" class="...xml.BeanExample" factory-method="getInstance"/>
2.3 實(shí)例工廠方式實(shí)例化
和靜態(tài)工廠方法一樣,不同的是工廠方法是實(shí)例化后的 Bean 的方法而不是靜態(tài)方法掖棉。
public class BeanExampleFactory {
private static BeanExample beanExample = new BeanExample();
public BeanExample getInstance() {
return beanExample;
}
}
在 Bean 配置中使用 factory-bean
屬性指定工廠類的 Bean,使用 factory-method
屬性來(lái)指定工廠方法膀估。
<bean id="beanExample" class="...xml.BeanExample" factory-bean="beanExampleFactory" factory-method="getInstance"/>
<bean id="beanExampleFactory" class="cn.codeartist.spring.bean.xml.BeanExampleFactory"/>
3. Bean 作用域
通過(guò) scope
屬性配置 bean 的作用域幔亥,來(lái)指定 bean 的實(shí)例化作用范圍。
<bean id="beanExample" class="...xml.BeanExample" scope="prototype"/>
常用的幾種 Bean 作用域如下:
作用域 | 描述 |
---|---|
singleton |
(默認(rèn))單例作用域玖像,在 Spring 容器內(nèi)部只創(chuàng)建一個(gè)實(shí)例 |
prototype |
原型作用域紫谷,在容器中創(chuàng)建多個(gè)實(shí)例,每使用一次創(chuàng)建一個(gè)實(shí)例 |
request |
請(qǐng)求作用域捐寥,在 Web 框架下單次請(qǐng)求創(chuàng)建一個(gè)實(shí)例 |
session |
會(huì)話作用域笤昨,在 Web 框架下單次會(huì)話內(nèi)創(chuàng)建一個(gè)實(shí)例 |
application |
應(yīng)用作用域,在 ServletContext 生命周期內(nèi)創(chuàng)建一個(gè)實(shí)例 |
二握恳、依賴注入
Spring 容器創(chuàng)建好了 Bean 實(shí)例后瞒窒,會(huì)根據(jù)實(shí)例間的依賴關(guān)系來(lái)進(jìn)行注入。
1. 依賴注入
1.1 構(gòu)造器注入
通過(guò)類的構(gòu)造器來(lái)注入依賴的值或 Bean乡洼。
<bean id="beanExample" class="...xml.BeanExample">
<constructor-arg index="0" value="碼匠公眾號(hào)"/>
<constructor-arg index="1" value="2021"/>
<constructor-arg index="2" ref="beanProvider"/>
</bean>
1.2 Setter 方法注入
通過(guò)類的 Setter 方法注入依賴的值或 Bean崇裁。
<bean id="beanExample" class="...xml.BeanExample">
<property name="name" value="碼匠公眾號(hào)"/>
<property name="year" value="2021"/>
<property name="beanProvider" ref="beanProvider"/>
</bean>
在兩種注入方式中,配置值的方式:
-
value
:注入值 -
ref
:注入引用(注入 Bean 實(shí)例)
2. 依賴關(guān)系
一般情況下束昵,Bean 之間的依賴關(guān)系并不明確拔稳,但在一些情況下,比如初始化一個(gè)靜態(tài)類锹雏,使用 depends-on
屬性指定在初始化該 bean 之前巴比,強(qiáng)制初始化依賴的一個(gè)或多個(gè) bean。
<bean id="beanExample" class="...xml.BeanExample" depends-on="beanProvider" />
3. 懶加載
一般情況下礁遵,Spring 會(huì)在容器啟動(dòng)的時(shí)候把所有 Bean 實(shí)例化完成轻绞,如果想在第一次使用的 Bean 的時(shí)候才初始化,可能配置 lazy-init
來(lái)實(shí)現(xiàn)佣耐。
<bean id="beanExample" class="...xml.BeanExample" lazy-init="true"/>
4. 自動(dòng)注入
Spring 容器支持自動(dòng)注入政勃,而不需要手動(dòng)通過(guò) ref
來(lái)指定依賴的 bean 實(shí)例。
<bean id="beanExample" class="...xml.BeanExample" autowire="byName"/>
容器支持的注入方式:
注入方式 | 描述 |
---|---|
no |
(默認(rèn))不使用自動(dòng)注入 |
byName |
通過(guò) bean 名稱注入 |
byType |
通過(guò) bean 類型注入 |
constructor |
通過(guò)構(gòu)造器參數(shù)類型注入 |
三兼砖、附錄
1. 配置屬性表
屬性 | 默認(rèn)值 | 描述 |
---|---|---|
id |
- | 指定 bean 的名稱 |
class |
- | 指定 bean 的類 |
scope |
singleton |
指定作用域 |
depends-on |
- | 指定依賴關(guān)系 |
lazy-init |
false |
配置懶加載 |
autowire |
no |
配置自動(dòng)注入 |
factory-bean |
- | 指定提供工廠方法的 bean |
factory-method |
- | 指定創(chuàng)建 bean 的工廠方法 |
2. 示例代碼
Gitee 倉(cāng)庫(kù):https://gitee.com/code_artist/spring
代碼目錄:src/main/java/cn/codeartist/spring/bean/xml
獲取最新教程關(guān)注碼匠公眾號(hào):CodeArtist