Spring三级缓存解决循环依赖必要性研讨

在这里插入图片描述

由于spring三级缓存处理逻辑的直接读源码比较难理解,所以一气之下按照方法压栈顺序整理了一张图供大家参考;图中各个环节标注了序号,之后的文章我会按照序号来给你标注出代码位置;可以看到整个过程中bean在三级缓存中的状态;

此篇不贴代码的原因是,我认为思想是指导代码的根髓,代码是对思想的表达。所以我们先学习心法,后看招式,不至于走火入魔

注: 虚线的框表示入栈后立马出栈,但是为了对称性,画在对称的位置

在这里插入图片描述

关于三级缓存必要性的讨论

首先对于第二级缓存的作用,都好理解:在bean真正创建完成之前先放在二级缓存中,防止提前暴露到一级缓存,导致并发场景下拿到空壳子下面开始讨论第三级缓存的必要性;

图中可以看到第2步那里是往第三级缓存放入了一个包含对A早期引用进行操作的工厂函数。在第10步的时候才取出来这个函数进行调用。那么如果我直接在第2步就执行这个函数的逻辑,然后把A直接放到2级缓存,废除掉第3级缓存,是不是可以呢?

答案是可以的;

但是为什么没这样做呢:

我们发现对A早期引用进行操作的工厂函数,在没有循环引用的时候甚至都不需要执行。那么spring的第三级缓存,让这段逻辑可执行也可以不执行。
那么这个三级缓存至少达到了一个目的就是,让这段逻辑只在需要执行的时候才会执行

这段逻辑做了什么事情呢?

如果有代理的话,那么提前对bean进行代理(正常情况下:bean生命周期中一般是要在bean实例化之后才生成代理);

也就是说循环依赖的时候把生成代理的逻辑提前了。那么spring希望bean在的生命周期存在异类吗?显然是不希望的;别无他法的时候它才去这样做;

那么如果只有两级缓存我们该怎么做?

方案1:把代理提前在第二步执行;
那么所有bean生命周期都会是提前进行代理了,缺点 就是:所有的单例bean的代理时机和初始化后才代理设计不符
方案2:把对A早期引用进行操作的工厂函数,也放到二级缓存里面呢
显然这种有可行性,但是二级缓存中又要存工厂函数又要存早期bean。二级缓存担任了多个职责,又显得不够优雅;缺点 就是:二级缓存的职责不明确

所以综上三级缓存尽在可能保证了bean的生命周期的正常的情况下,让每层缓存设计也更加美丽纯净。用深厚的内功耍出来优美的剑术,而且还不至于走火入魔,实在是高超,是剑宗和气宗的势均力敌博弈;

关于网上一些观点的看法:

1.有的说是为了进行aop代理:
反驳:不循环依赖就不需要aop代理了吗?
2.为了解决生命周期的统一
反驳:其实并没有解决生命周期统一。而是尽量解决大部分的是统一的,小部分有循环依赖的并没有解决

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值