Spring中的一切对象都被IoC容器托管,对象是合适加载,如何加载,什么时候销毁的呢。

Spring中Bean的生命周期

需要注意的地方

  1. BeanNameAware接口,需要实现setBeanName(String s)方法,Spring将bean的id传过来,一般没啥作用;
  2. BeanFactoryAware接口,实现setBeanFactory(BeanFactory beanFactory)方法,spring传递的容器工厂实例;
  3. ApplicationContextAwaer接口,实现setApplicationContext(ApplicationContext applicationContext)接口,传递过来的是应用上下文;
  4. BeanPostProcess接口,实现postProcessBeforeInitializationpostProcessAfterInitialization,bean初始化之前和之后的处理;
  5. InitializingBean接口,实现afterPropertiesSet,全部属性设置完成后执行;
  6. 使用后,如果bean实现了DispostbleBean接口,那么销毁的时候会执行destory方法。

如何解决循环依赖

spring在创建A的时候,发现需要依赖B,因为去创建B实例,发现B又依赖于A,又去创建A,因为形成一个闭环,无法停止下来就可能会导致cpu计算飙升。
spring解决这个问题主要靠巧妙的三层缓存,所谓的缓存主要是指这三个map,singletonObjects主要存放的是单例对象,属于第一级缓存;
singletonFactories属于单例工厂对象,属于第三级缓存;earlySingletonObjects属于第二级缓存,如何理解early这个标识呢?它表示只是经过了实例化尚未初始化的对象。
Spring首先从singletonObjects(一级缓存)中尝试获取,如果获取不到并且对象在创建中,则尝试从earlySingletonObjects(二级缓存)中获取,如果还是获取不到并且允许从singletonFactories通过getObject获取,则通过singletonFactory.getObject()(三级缓存)获取。
如果获取到了则移除对应的singletonFactory,将singletonObject放入到earlySingletonObjects,其实就是将三级缓存提升到二级缓存,这个就是缓存升级。
spring在进行对象创建的时候,会依次从一级、二级、三级缓存中寻找对象,如果找到直接返回。由于是初次创建,只能从第三级缓存中找到(实例化阶段放入进去的),创建完实例,然后将缓存放到第一级缓存中。下次循环依赖的再直接从一级缓存中就可以拿到实例对象了。