bean的生命周期:从bean被实例化到销毁。
本文的工程目录如下:
通过init_method和destroy_method实现
相关代码片
//applicationContext.xml
<bean id="flowDao" class="com.lwb.dao.impl.FlowDaoImpl" init-method="init" destroy-method="destroy"/>
//FlowDaoImpl.java
public class FlowDaoImpl implements FlowDao{
@Override
public void save() {
System.out.println(this.getClass() + "------进入FLowDaoImpl");
}
//bean的生命周期
public void init(){
System.out.println(this.getClass() + "-----进入FlwoDaoImpl初始化方法init");
}
public void destroy(){
System.out.println(this.getClass() + "-----进入FlwoDaoImpl销毁方法destroy");
}
}
//App.java
public class App {
public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
}
}
执行结果:
思考:
1、bean的初始化方法是什么时候执行的?
bean的初始化方法是在bean对象实例化后执行的。Spring单例+懒惰式,在初始化IOC容器后会对bean进行实例化。可把flowDao对象设置成非实例验证,发现init方法未被执行。
2、destroy方法为什么没有执行?
main方法执行-》jvm运行-》ioc容器创建-》执行init方法-》main方法执行结束。需要手动调用destroy方法。Spring提供了两种方法调用destroy方法。如下:
代码片
//App.java
public class App {
public static void main(String[] args) {
//ApplicationContext换成ClassPathXmlApplicationContext
ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
FlowDao flowDao = (FlowDao) ctx.getBean("flowDao");
flowDao.save();
//方法一、调用close()方法手动销毁
ctx.close();
//方法二、提供钩子函数,供jvm退出前回调该函数
//ctx.registerShutdownHook();
}
}
执行结果:
思考:
1、close()和registerShutdownHook()方法有什么区别?
执行时机不同。close()在手动调用的时候执行,registerShutdownHook()在jvm退出的时候。可如下进行验证,执行后发现:
close():“------在这儿还没有关闭"在destroy后;
registerShutdownHook():”------在这儿还没有关闭"在destroy前。
证明了我们的猜想。
代码片
//App.java
public class App {
public static void main(String[] args) {
//ApplicationContext换成ClassPathXmlApplicationContext
ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
FlowDao flowDao = (FlowDao) ctx.getBean("flowDao");
flowDao.save();
//方法一、调用close()方法手动销毁
ctx.close();
//方法二、提供钩子函数,供jvm退出前回调该函数
//ctx.registerShutdownHook();
System.out.println("------在这儿还没有关闭");
}
}
通过继承接口实现
相关代码片
//applicationContext.xml
<bean id="flowDao" class="com.lwb.dao.impl.FlowDaoImpl"/>
//FlowDaoImpl.java
public class FlowDaoImpl implements FlowDao,InitializingBean,DisposableBean {
public FlowDaoImpl() {
System.out.println(this.getClass() + "--------进入构造器");
}
@Override
public void save() {
System.out.println(this.getClass() + "------进入FLowDaoImpl");
}
@Override
public void afterPropertiesSet() throws Exception {
System.out.println(this.getClass() + "------init");
}
@Override
public void destroy() throws Exception {
System.out.println(this.getClass() + "------destroy");
}
}
//App.java
public class App {
public static void main(String[] args) {
//ApplicationContext换成ClassPathXmlApplicationContext
ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
FlowDao flowDao = (FlowDao) ctx.getBean("flowDao");
flowDao.save();
//方法一、调用close()方法手动销毁
ctx.close();
//方法二、提供钩子函数,供jvm退出前回调该函数
//ctx.registerShutdownHook();
System.out.println("------在这儿还没有关闭");
}
}
结果:
思考:
1、该方法,销毁时还是需要调用close方法或者钩子函数。
2、afterPropertiesSet意思为设置属性后,即在构造方法后执行。
(说明:该文章为学习黑马教程后的实现和思考)