Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/384.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么Spring对待构造函数注入与setter/字段注入不同?_Java_Spring - Fatal编程技术网

Java 为什么Spring对待构造函数注入与setter/字段注入不同?

Java 为什么Spring对待构造函数注入与setter/字段注入不同?,java,spring,Java,Spring,我在project中遇到了一个循环依赖的小问题,并发现在字段/设置器上使用@Autowired可以解决这个问题,而不是在构造函数上使用@Autowired。这种行为的结论是,Spring在字段/设置器注入的情况下注入代理,在构造函数注入的情况下注入实际bean 问题是: 这背后的原因是什么?为什么注入不同的实体 考虑一下简单的代码片段: @Component public static class A{ @Autowired B b; @Autow

我在project中遇到了一个循环依赖的小问题,并发现在字段/设置器上使用
@Autowired
可以解决这个问题,而不是在构造函数上使用
@Autowired
。这种行为的结论是,Spring在字段/设置器注入的情况下注入代理,在构造函数注入的情况下注入实际bean

问题是: 这背后的原因是什么?为什么注入不同的实体

考虑一下简单的代码片段:

    @Component
    public static class A{
        @Autowired B b;
        @Autowired C c;
    }
    @Component
    public static class B{
        @Autowired B b;
        @Autowired C c;
//      public B(C c,B b) { // this would cause circular dep problem
//          this.c=c;
//      }
    }
    @Component
    public static class C{
        @Autowired A a;
        @Autowired B b;
    }

我想到的一个想法是,通过构造函数注入,您可以立即使用注入的实体,因此,作为预生成初始化的bean被注入,而不是代理,但另一方面,我可以在setter方法中做同样的事情,所以,当您使用构造函数注入时,构造函数中使用的所有bean都必须提前创建。如果您有循环依赖项,则无法创建它们,因为循环依赖项和spring抛出异常

当您使用setter/field注入时,注入的元素是在创建bean之后设置的,所以允许循环依赖


顺便说一句,如果您有循环依赖,请尝试重新设计您的应用程序,因为您的代码将更难维护。这是首选构造函数注入的原因之一。

您证明了它是一个代理吗?这应该很容易做到:只需打印thing.getClass().getName()。我认为代理根本不重要。根据这一点,构造函数注入和setter注入是等价的,这是完全错误的。时期在构造函数注入中,预期参数是完全构造的,但当出现循环依赖时,这是不可能的。因此,他们决定干脆把它当作一个错误。在setter注入中,您知道当作为参数传递时,参数可能不会完全构造。@rghome可能不会,这只是我的结论。此外,我认为它是一个代理,因为它有空字段,是一个“增强”类。不管它是否是代理,行为都是确定的。我只是想知道背后的原因this@GiacomoAlzetta感谢您指出文档。有趣的是,有这么多知识是如此的丰富。听起来很合理,这里最重要的部分是注入发生的时间点——对于字段/设置器,所有注入都是在创建每个bean实例之后完成的,而对于ctor,这可能是不可能的。