此博客為學(xué)習(xí)筆記,記錄下來(lái)怕自己后面學(xué)著學(xué)著忘記了。
CSDN內(nèi)容同步更新,id同名,本文CSDN鏈接
Spring Bean
Spring5基礎(chǔ)(2)——Spring IoC控制反轉(zhuǎn)(基礎(chǔ))
在上一篇文章中講述到Spring IoC容器創(chuàng)建實(shí)例對(duì)象,淺顯的在xml文件中配置了需要注入的實(shí)例對(duì)象。
更具體一步來(lái)說(shuō)應(yīng)該是Spring IoC容器可以創(chuàng)建,裝配和配置應(yīng)用組件對(duì)象(該對(duì)象稱為Bean),這篇文章將從配置屬性+實(shí)例化+作用域3個(gè)方面詳解Bean。下一篇文章再記錄Bean的生命周期與裝配方式。
Spring Bean的配置——<bean>元素常用屬性及其子元素
在上篇文章中也有過(guò)在xml中對(duì)bean的基本配置,下列是bean元素常用屬性及其子元素:
屬性:
id:Bean在BeanFactory中唯一標(biāo)識(shí),使用BeanFactory獲取實(shí)例時(shí)以此為索引名,.getBean()方法時(shí)傳入id。
class:具體實(shí)現(xiàn)類,如com.lipiao.demo.B
scope:指定Bean的作用域,本文后面會(huì)提到。子元素名稱:
< constructor-arg > :使用構(gòu)造方法注入Bean,還可指定構(gòu)造方法參數(shù)。該元素下的index屬性表示參數(shù)序號(hào),ref屬性表示對(duì)BeanFactory中其他Bean的引用關(guān)系,type屬性表示參數(shù)類型,value屬性表示參數(shù)的常量值。
< property > :用于設(shè)置Bean的一個(gè)屬性。該元素下的name屬性用于指定設(shè)置該Bean哪個(gè)屬性,填入對(duì)應(yīng)屬性名稱。value屬性即指定屬性的屬性值。ref屬性表示對(duì)BeanFactory中其他Bean的引用關(guān)系。
< list > :用于封裝List或數(shù)組類型的依賴注入。
< map > :用于封裝Map類型的依賴注入。
< set > :用于封裝Set類型的依賴注入。
< enty > :用于設(shè)置一個(gè)鍵值對(duì)。
< list >、< map >、< set >、< enty >這四個(gè)子元素會(huì)在下一篇文章記錄Bean裝配方式中會(huì)提到:
了解完屬性之后再回過(guò)頭去看上篇文章在xml文件的配置信息就一目了然啦。
舉個(gè)栗子:
package com.lipiao.demo;
public class A {
String name;
public void setName(String name) {
this.name = name;
}
}
在applicationContext.xml中配置該類如下所示:
<bean id="A4_1" class="com.lipiao.demo.A">
<property name="name" value="A4_1"></property>
</bean>
這里就是對(duì)com.lipiao.demo.A這個(gè)類(class)進(jìn)行配置,設(shè)置唯一標(biāo)識(shí)符(id)為A4_1。使用bean的子元素property為該類設(shè)置一個(gè)屬性,設(shè)置的屬性名稱(name)為name,設(shè)置的屬性值(value)為A4_1.
我們?cè)谑褂肂ean的時(shí)候就可以通過(guò)配置信息中的唯一標(biāo)識(shí)符(id)獲取該實(shí)例對(duì)象啦,使用getBean方法傳入id,如下所示:
//4.1 ClassPathXmlApplicationContext 使用相對(duì)路徑(resources根目錄)
ApplicationContext applicationContext4_1 =
new ClassPathXmlApplicationContext("META-INF/applicationContext.xml");
A a4_1= (A) applicationContext4_1.getBean("A4_1");
Spring Bean的實(shí)例化——構(gòu)造方法,靜態(tài)工廠,實(shí)例工廠
-
構(gòu)造方法實(shí)例化
Spring容器可以調(diào)用Bean對(duì)應(yīng)類中的無(wú)參構(gòu)造方法來(lái)實(shí)例化Bean,這就是構(gòu)造方法實(shí)例化。
其實(shí)剛剛使用A類的時(shí)候就是通過(guò)無(wú)參構(gòu)造實(shí)例化(不寫(xiě)構(gòu)造默認(rèn)會(huì)有一個(gè)無(wú)參構(gòu)造),就不重復(fù)舉例了。
修改A類代碼如下,刪掉set,添加一個(gè)有參構(gòu)造方法,補(bǔ)上無(wú)參構(gòu)造,接下來(lái)的兩個(gè)實(shí)例化Bean方法基于此A類:
package com.lipiao.demo;
public class A {
String name;
public A() {
}
public A(String name) {
this.name = name;
}
}
-
靜態(tài)工廠實(shí)例化
①創(chuàng)建工廠類BeanStaticFactory
在工廠類中創(chuàng)建一個(gè)靜態(tài)方法來(lái)創(chuàng)建Bean的實(shí)例
package com.lipiao.demo;
public class BeanStaticFactory {
private static A a=new A("靜態(tài)工廠實(shí)例化");
public static A createA(){
return a;
}
}
②applicationContext.xml總添加配置信息
<!-- 靜態(tài)工廠實(shí)例化-->
<bean id="staticFactory"
class="com.lipiao.demo.BeanStaticFactory"
factory-method="createA"></bean>
其中factory-method屬性即調(diào)用工廠類中的方法,例子中時(shí)調(diào)用createA();
③獲取該實(shí)例化Bean
//Spring Bean 2.靜態(tài)工廠實(shí)例化
ApplicationContext applicationContext5_2 =
new ClassPathXmlApplicationContext("META-INF/applicationContext.xml");
A a5_2= (A) applicationContext5_2.getBean("staticFactory");
System.out.println(a5_2.name);
運(yùn)行效果:
信息: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@23ab930d: startup date [Thu Jul 18 23:33:13 CST 2019]; root of context hierarchy
七月 18, 2019 11:33:14 下午 org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
信息: Loading XML bean definitions from class path resource [META-INF/applicationContext.xml]
靜態(tài)工廠實(shí)例化
-
實(shí)例工廠實(shí)例化
①創(chuàng)建工廠類BeanInstanceFactory
在工廠類中創(chuàng)建一個(gè)實(shí)例方法來(lái)創(chuàng)建Bean的實(shí)例
package com.lipiao.demo;
public class BeanInstanceFactory {
public A createA() {
return new A("實(shí)例工廠實(shí)例化");
}
}
②applicationContext.xml總添加配置信息
首先配置實(shí)例工廠類,之后使用factory-bean屬性配置指定的配置工廠,factory-method屬性指定實(shí)例工廠中的實(shí)例方法。
<!-- 實(shí)例工廠實(shí)例化-->
<!-- 配置工廠-->
<bean id="myFactory" class="com.lipiao.demo.BeanInstanceFactory"/>
<bean id="instanceFactory" factory-bean="myFactory" factory-method="createA"/>
③獲取該實(shí)例化Bean
//Spring Bean 3.實(shí)例工廠實(shí)例化
ApplicationContext applicationContext5_3 =
new ClassPathXmlApplicationContext("META-INF/applicationContext.xml");
A a5_3= (A) applicationContext5_3.getBean("instanceFactory");
System.out.println(a5_3.name);
運(yùn)行效果:
七月 18, 2019 11:49:30 下午 org.springframework.context.support.AbstractApplicationContext prepareRefresh
信息: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@4566e5bd: startup date [Thu Jul 18 23:49:30 CST 2019]; root of context hierarchy
七月 18, 2019 11:49:30 下午 org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
信息: Loading XML bean definitions from class path resource [META-INF/applicationContext.xml]
實(shí)例工廠實(shí)例化
Spring Bean的作用域
完成實(shí)例化Bean之后,還可以指定Bean的作用域。
一共六種,前兩者常用,后四種僅在Web Spring應(yīng)用程序上下文中使用。
- singleton:這是默認(rèn)的作用域,Spring容器中只有一個(gè)Bean實(shí)例,即容器內(nèi)為單例模式。
- prototype:Spring容器每次獲取該作用域的Bean實(shí)例時(shí),都會(huì)新建一個(gè)Bean實(shí)例。
- request:在一次HTTP請(qǐng)求中將返回一個(gè)Bean實(shí)例,不同的HTTP請(qǐng)求返回不同實(shí)例。
- session:在一次HTTP session中返回一個(gè)Bean實(shí)例。
- application:為每個(gè)ServletContext對(duì)象創(chuàng)建實(shí)例,即同一應(yīng)用共享一個(gè)Bean實(shí)例。
- websocket:為每個(gè)websocket對(duì)象創(chuàng)建實(shí)例。