5.1 生命周期
1> Spring对bean进行实例化
2> Spring将value或者ref(bean的引用)注入到bean的属性中
3> 如果bean实现了aware接口(例如BeanNameAware和ApplicationContextAware),则Spring会调用接口中定义的回调方法
4> 执行BeanPostProcessor的postProcessBeforeInitialization方法
5> Spring调用初始化回调
6> 执行BeanPostProcessor的postProcessAfterInitialization方法
7> bean准备就绪,可以被应用使用
8> Spring调用销毁回调
5.2 Bean 的三种初始化和销毁回调:
(1)@PostContruct和@PreDestroy
这两个注解是JSR-250中的,不属于Spring,所以如果使用了也不会跟Spring产生耦合。如果一个类中有多个方法被标注成@PostContruct或@PreDestory,那么容器会依次调用这些方法;
(2)实现InitializingBean和DisposableBean接口。这两个接口分别有afterPropertiesSet()和detroy()方法,容器会在特定的时机回调这两个方法;
(3)在xml配置文件中的元素中设置init-method和destroy-method属性,指定初始化方法和销毁方法的方法名;
此外,还可以在元素中统一设置初始化和销毁方法的名字,属性为default-init-method和default-destroy-method。元素的的init-method和destroy-method会覆盖元素中的配置。
5.3 三种机制的执行顺序
上述的三种生命周期机制可以一起使用。如果使用多种机制,并且每种机制都配置了不同的方法名,那么每个被配置的方法会依次执行。如果方法名相同,则该方法只会执行一次。
初始化:
(1)被@PostConstruct注解的方法;(2)afterPropertiesSet()方法;(3)在xml中配置的init-method;
销毁:
(1)被@PreDestroy注解的方法;(2)destroy()方法;(3)在xml中配置的destroy
销毁过程需要Spring优雅的关闭时才会执行。优雅的关闭非web应用中的Spring IoC容器的方式:ConfigurableApplicationContext接口的registerShutdownHook()方法。
4.2.3 使用@Qualifier指定注入Bean的名称
如果容器中有一个以上匹配的Bean时,则可以通过@Qualifier注解限定Bean的名称: 这里假设容器有两个类型为 ILbsMapMatchThriftService.Iface 的Bean,一个名为 lbsRoadMapService ,另一个名为 lbsMapMatchServices,两处会分别注入,若不进行区分,注入时会报错。
如果将红色框中的 @Qualifier 进行注释,运行相应测试用例时,报出如下错误:
多路复用IO是在高并发场景中使用最为广泛的一种IO模型,如Java的NIO、Redis、Nginx的底层实现就是此类IO模型的应用,经典的Reactor模式也是基于此类IO模型。
那么什么是IO多路复用呢?通过字面上的理解,多路就是指多个通道,也就是多个网络连接的IO,而复用就是指多个通道复用在一个复用器上。
多个网络连接的IO可以注册到一个复用器(select)上,当用户进程调用了select,那么整个进程会被阻塞。同时,内核会“监视”所有select负责的socket,当任何一个socket中的数据准备好了,select就会返回。这个时候用户进程再调用read操作,将数据从内核中拷贝到用户进程。
这里我们可以看到,当用户进程发起了select调用,进程会被阻塞,当发现该select负责的socket有准备好的数据时才返回,之后才发起一次read,整个流程要比阻塞IO要复杂,似乎也更浪费性能。但它最大的优势在于,用户可以在一个线程内同时处理多个socket的IO请求。用户可以注册多个socket,然后不断地调用select读取被激活的socket,即可达到在同一个线程内同时处理多个IO请求的目的。而在同步阻塞模型中,必须通过多线程的方式才能达到这个目的。