|Spring循环依赖,我本来都不想写的,但网上好多错误观点( 四 )


是的 , 这个思路看起来没任何问题 ,问题就出在时机, 这跟 Bean 的生命周期有关系 。
正常代理对象的生成是基于后置处理器 , 是 在被代理的对象初始化后期调用生成的,所以如果你提早代理了其实是违背了 Bean 定义的生命周期。
所以 Spring 先在一个三级缓存放置一个工厂 , 如果产生循环依赖 , 那么就调用这个工厂提早得到代理对象 。
如果没产生依赖 , 这个工厂根本不会被调用 , 所以 Bean 的生命周期就是对的 。
至此 , 我想你应该明白为什么会有三级缓存了 。
也明白 , 其实破坏循环依赖 , 其实只有二级缓存就够了 , 但是碍于生命周期的问题 , 提前暴露工厂延迟代理对象的生成 。
对了 , 不用担心三级缓存因为没有循环依赖 , 数据堆积的问题 , 最终单例 Bean 创建完毕都会加入一级缓存 , 此时会清理下面的二、三级缓存 。

最后好了 , 看到这里想必你应该对 Spring 的循环依赖很清晰了 , 并且面试的时候肯定也难不倒你了 。
我稍微总结下:

  • 有构造器注入 , 不一定会产生问题 , 具体得看是否都是构造器注和 BeanName 的字母序
  • 如果单纯为了打破循环依赖 , 不需要三级缓存 , 两级就够了 。
  • 三级缓存是否为延迟代理的创建 , 尽量不打破 Bean 的生命周期