Spring循环依赖:

Spring循环依赖:,第1张

去看,去看,去看
课程:这个老师讲的还是很清晰的:
https://www.bilibili.com/video/BV1vR4y1J7cv?p=41

三级缓存

三个缓存分别有什么作用
  • 第一层缓存(singletonObjects):单例对象缓存池,已经实例化并且属性赋值,这里的对象是成熟对象;
  • 第二层缓存(earlySingletonObjects):单例对象缓存池,已经实例化但尚未属性赋值,这里的对象是半成品对象;
  • 第三层缓存(singletonFactories): 单例工厂的缓存
什么是循环依赖

总:什么是循环依赖问题,A依赖B,B依赖A
分:先说明bean的创建过程:实例化,初始化(填充属性)
1、先创建A对象,实例化A对象,此时A对象中的b属性为空,填充属性b
2、从容器中查找B对象,如果找到了,直接赋值不存在循环依赖问题(不通),找不到 直接创建B对象
3、实例化B对象,此时B对象中的a属性为空,填充属性a
4、从容器中查找A对象,找不到,直接创建


形成闭环的原因

此时,如果仔细琢磨的话,会发现A对象是存在的,只不过此时的A对象不是一个完整的状态,只完成了实例化但是未完成初始化,如果在程序调用过程中,拥有了某个对象的引用,能否在后期给他完成赋值 *** 作,可以优先把非完整状态的对象优先赋值,等待后续 *** 作来完成赋值,相当于提前暴露某个不完整对象的引用,所以解决问题的核心在于实例化和初始化分开 *** 作,这也是解决循环依赖问题的关键,

如何打破上面的循环;加个缓存就好了(暴露某个不完整对象的引用)。



aService的生命周期;
1、实例化 原始对象 ----> Map(beanName,原始对象)>
2、填充bService的属性—> 单例池中去找bService对应的对象,----> 没有找到—>从Map(beanName,原始对象)去找---->aService原始对象
3、填充其他属性
4、AOP
5、放入单例池

bService的生命周期;
1、实例化 原始对象 ----> Map(beanName,原始对象)>
2、填充aService的属性—> 单例池中去找aService对应的对象,—> 没有找到—> 从Map(beanName,原始对象)去找---->找到了
3、填充其他属性
4、AOP
5、放入单例池

注意:B的对于A的属性填充创建完毕之后,就相当于,A属性也填充完了。


思考: 这里二级缓存就就可以解决循环依赖,为什么还要三级缓存?三级缓存又解决了什么问题?

为什么需要三级缓存?

三级缓存的value类型是ObjectFactory,是一个函数式接口,存在的意义是保证在整个容器的运行过程中同名的bean对象只能有一个。


解决的问题:

我们属性填充的原始的对象,如果一个对象需要被代理(AOP),或者说需要生成代理对象,那么要不要优先生成一个普通对象?要
普通对象和代理对象是不能同时出现在容器中的,因此当一个对象需要被代理的时候,就要使用代理对象覆盖掉之前的普通对象,在实际的调用过程中,是没有办法确定什么时候对象被使用,所以就要求当某个对象被调用的时候,优先判断此对象是否需要被代理,类似于一种回调机制的实现,因此传入lambda表达式的时候,可以通过lambda表达式来执行对象的覆盖过程,getEarlyBeanReference()

引用:https://blog.csdn.net/weixin_44129618/article/details/122839774

重点:
当Bean出现循环依赖的情况 进行,提前AOP *** 作:

在哪里知道程序出现了循环依赖:在bService 的给A 进行属性填充的时候,依赖于A 的创建,这时候我们就可以做出判断,提前进入AOP。


得到aService的代理对象。




三级缓存的作用是什么:
要想实现AOP,即我们生成的代理对象。


还有必须拿到实例化对象的原始对象(即AService的原始对象)。


怎么使这两者连接起来那,三级缓存 Map

AbstractAutoProxyCreator的类

DefaultSingletonBeanRegistry的类

因此,所有的bean对象在创建的时候都要优先放到三级缓存中,在后续的使用过程中,如果需要被代理则返回代理对象,如果不需要被代理,则直接返回普通对象。


当三级缓存执行完之后,移除,放入到二级缓存中,当二级缓存执行完之后,放入到一级缓存中。


欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/langs/607219.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-04-14
下一篇 2022-04-14

发表评论

登录后才能评论

评论列表(0条)

保存