Spring是如何解决循环依赖的

简介

所谓循环依赖指的是:BeanA对象的创建依赖于BeanB,BeanB对象的创建也依赖于BeanA,这就造成了死循环,如果不做处理的话势必会造成栈溢出。Spring通过提前曝光机制,利用三级缓存解决循环依赖问题。

变量 描述
singletonObjects 一级缓存,key为Bean名称,value为Bean实例。这里的Bean实例指的是已经完全创建好的,即已经经历实例化->属性填充->初始化以及各种后置处理过程的Bean,可直接使用。
earlySingletonObjects 二级缓存,key为Bean名称,value为Bean实例。这里的Bean实例指的是仅完成实例化的Bean,还未进行属性填充等后续操作。用于提前曝光,供别的Bean引用,解决循环依赖。
singletonFactories 三级缓存,key为Bean名称,value为Bean工厂。在Bean实例化后,属性填充之前,如果允许提前曝光,Spring会把该Bean转换成Bean工厂并加入到三级缓存。在需要引用提前曝光对象时再通过工厂对象的getObject()方法获取。

加入三级缓存解决循环依赖

假设容器先创建BeanA,属性填充时,发现BeanA依赖BeanB,然后Spring开始创建BeanB。创建BeanB时候又发现其依赖BeanA,这时三级缓存中已经存在BeanA的工厂对象了,所以直接通过该工厂对象获取BeanA的早期实例,因此不会抛出循环依赖异常。

总结

虽然spring已经加入三级缓存解决绝大部分循环依赖的问题,但是我们在编码过程中仍然不建议出现循环依赖,因为这会增加代码的复杂度,不利于排查问题。

相关推荐
pianmian134 分钟前
类(JavaBean类)和对象
java
我叫小白菜1 小时前
【Java_EE】单例模式、阻塞队列、线程池、定时器
java·开发语言
Albert Edison2 小时前
【最新版】IntelliJ IDEA 2025 创建 SpringBoot 项目
java·spring boot·intellij-idea
超级小忍2 小时前
JVM 中的垃圾回收算法及垃圾回收器详解
java·jvm
weixin_446122462 小时前
JAVA内存区域划分
java·开发语言·redis
Piper蛋窝3 小时前
深入 Go 语言垃圾回收:从原理到内建类型 Slice、Map 的陷阱以及为何需要 strings.Builder
后端·go
勤奋的小王同学~3 小时前
(javaEE初阶)计算机是如何组成的:CPU基本工作流程 CPU介绍 CPU执行指令的流程 寄存器 程序 进程 进程控制块 线程 线程的执行
java·java-ee
TT哇3 小时前
JavaEE==网站开发
java·redis·java-ee
2401_826097623 小时前
JavaEE-Linux环境部署
java·linux·java-ee
缘来是庄3 小时前
设计模式之访问者模式
java·设计模式·访问者模式