Spring中自动注入的两种方式总结
作者:白胡子永远 时间:2022-10-24 08:54:14
1. 前言
Spring的核心技术IOC(Intorol of Converse控制反转)的实现途径是DI(dependency Insert依赖注入)。而依赖注入(DI)的实现方式又有两种,xml方式和注解方式。如下图所示:
2. set注入和构造注入
set注入和构造注入,这两种方法,是我们在第一次接触Spring的时候,最先学习使用Spring容器创建对象并赋值的方式。具体的代码及详细解释我已经写在了我前一篇的文章里,这里的链接:点进去就能看到很仔细的set注入和构造注入的详细介绍和使用方法。
3. 什么情况下要使用自动注入
在我们学习完set注入和构造注入之后,我们可能会发现,要是某个类的引用属性,也是其他类的属性的时候,若我们使用大量的使用<propterty name="" ref="">去给其他类的这个引用属性赋值,就会显得十分的冗余。如下所示:
<beans>
<bean id="a" class="">
<property name="" value=""/>
<property name="11" ref="22"/> <!-某个引用类型的属性是很多其他类的属性-->
</bean>
<bean id="b" class="">
<property name="" value=""/>
<property name="11" ref="22"/> <!-某个引用类型的属性是很多其他类的属性-->
</bean>
<bean id="c" class="">
<property name="" value=""/>
<property name="11" ref="22"/><!-某个引用类型的属性是很多其他类的属性-->
</bean>
<bean id="d" class="">
<property name="" value=""/>
<property name="11" ref="22"/><!-某个引用类型的属性是很多其他类的属性-->
</bean>
</beans>
上面的写法就很冗余,那么有简单的写法吗?当然有,这种简便的方法就是自动注入。
4. 自动注入之byName
下面紧挨着的代码就是自动注入中的byName方式。
byName自动注入的特点就是,在<bean>标签中多写上了一个属性,type="byName"。
<bean id="" class="" type="byName">
<property name="" value=""/> <!--给基本类型属性赋值,不能使用byName自动注入-->
<property name="" ref=""/> <!--引用类型属性赋值,可以使用byName自动注入,进而实现简写-->
</bean>
byName自动注入的使用要求:
必须依赖set()方法,也就是说只支持对set注入方式的简写。
<bean>
<property name="" value=""/>
<property name="" ref=""/>
</bean>
不支持构造注入。
<bean>
<constructor-arg name="" value=""/>
</bean>
且只支持为引用类型属性赋值的时候使用byName的方式实现给引用类型属性赋值;给简单类型的属性赋值,不能使用byName这种构造注入,需要正常写。
那么在给引用类型的属性赋值的时候,使用了byName自动注入,那么我们便可以不写<property name="" ref="">。那byName是如何实现给给引用类型属性赋值的呢?
答案是:当Spring发现你使用了byName这种自动注入的时候,它会自动去寻找当前<bean>标签的class类,并去查看该类的引用属性有哪些,然后去当前xml文件中,去比对寻找是否有其他的<bean>标签的id等于该类的引用属性名,和其他<bean>标签的class属性值是否跟当前要赋值的引用属性的类是否一致。若是id和class都匹配上了,那么就会为该引用类型属性赋值。
5. 自动注入之byType注入
下面紧挨着的代码就是自动注入中的byType方式。
byType自动注入的特点就是,在<bean>标签中多写上了一个属性,type="byType"。byType自动注入的方式,跟byName的使用方法和要求几乎一模一样,只是在匹配赋值的时候,略有差别。
<bean id="" class="" type="byType">
<property name="" value=""/> <!--给基本类型属性赋值,不能使用byType自动注入,需要正常写-->
<property name="" ref=""/> <!--引用类型属性赋值,可以使用byType自动注入,进而实现简写-->
</bean>
<!---->
byType自动注入的使用要求:
必须依赖set方法,因此必须是对set注入方法的简写
支持set注入:如下所示
<bean>
<property name="" value=""/>
<property name="" ref=""/>
</bean>
不支持构造注入:如下所示
<bean>
<constructor-arg name="" value=""/>
</bean>
只支持给set注入中的引用类型属性赋值时候简写,不支持给set注入中的简单类型赋值,(给set注入中的简单类型赋值,仍需要正常写)如下所示
<bean id="" class="">
<property name="" value=""/> <!--给基本类型属性赋值,不能使用byType自动注入,需要正常写-->
<property name="" ref=""/> <!--引用类型属性赋值,可以使用byType自动注入,进而实现简写-->
</bean>
那么但给引用类型的属性赋值的时候,使用了byType自动注入,那么我们便可以不写<property name="" ref="">。那byType是如何实现给给引用类型属性赋值的呢?
答案是:Spring在见到byType自动注入的时候,会自动匹配其他的<bean>标签的class是否跟当前要创建的对象的引用类型属性是否是,子类,或者是接口实现类。若是则就会自动将匹配上的引用类型的值赋值给当前创建对象的引用类型属性。
!!注意!!:
由于Spring是单例模式,所以在使用自动注入给引用类型的属性匹配的<bean>标签的时候,若是匹配上了两个<bean>标签就会报错。
来源:https://blog.csdn.net/weixin_44362089/article/details/127347641