Bean的自动装配.
- 自动装配是Spring满足bean依赖一种方式
- Spring会在上下文中自动寻找,并自动给bean装配属性
在Spring中有三种装配方式.
- 在xml中装配
- 在java中装配
- 隐式的自动装配(autowired):将Bean自动注入到另一个Bean中
目录结构
环境搭建.
1、实体类.
Cat
public class Cat {
public void shout(){
System.out.println("miao~");
}
}
Dog
public class Dog {
public void shout(){
System.out.println("wang~");
}
}
People
@Data
public class People {
String name;
Cat cat;
Dog dog;
public void run(){
cat.shout();
dog.shout();
}
}
2、beans.xml
.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="cat" class="pojo.Cat"/>
<bean id="dog" class="pojo.Dog"/>
<!-- <bean id="people" class="pojo.People">-->
<!-- <property name="name" value="小伙子"/>-->
<!-- <!– 手动加载bean –>-->
<!-- <property name="cat" ref="cat"/>-->
<!-- <property name="dog" ref="dog"/>-->
<!-- </bean>-->
<!-- 自动装载 -->
<bean id="people" class="pojo.People" autowire="byName">
<property name="name" value="小伙子"/>
<!--
byName == 会自动在容器上下文中扫描,和自己对象set方法名中set后的单词匹配的 bean的id,要保证 id唯一, id是全小写的,然后自动加载
byType == 会自动在容器上下文中扫描,和自己对象属性的类型匹配的 bean的class,要保证 class的唯一,需要对应的set方法,然后自动加载
-->
</bean>
</beans>
- byName == 会自动在容器上下文中扫描,和自己对象set方法名中set后的单词匹配的 bean的id,要保证 id唯一, id是全小写的,然后自动加载(bean中的id 和 class 都要存在)
- byType == 会自动在容器上下文中扫描,和自己对象属性的类型匹配的 bean的class,要保证 class的唯一,需要对应的set方法,然后自动加载 (bean中的class要存在)
3、测试类.
public class MyTest {
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
People people = context.getBean("people", People.class);
people.run();
}
}
4、测试结果.
注解实现自动加载.
JDK1.5
支持注解
spring2.5
支持注解
开启注解(beans.xml).
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<!-- 自动装载注解支持 开启 -->
<context:annotation-config/>
<bean id="cat" class="pojo.Cat"/>
<bean id="dog" class="pojo.Dog"/>
<bean id="people" class="pojo.People"/>
</beans>
使用注解 @Autowired
.
- 在需要装载的属性前 添加
@Autowired
,也可以放在set方法前 - 使用了这个注解,可以不用编写set方法,前提是你这个自动装载的ioc容器中存在,且符合byType,和符合byName
@Autowired
- 先去容器中找 是否存在 与属性 类型一致的所有
Bean
,即Bean
的class
与 复杂属性的类型相同(byType); - 如果只存在一个 这样的
Bean
,就不管Bean
的id
是啥,就可以直接匹配; - 否则,就会在这些
Bean
中找与属性名相同的Bean
,即Bean
的id
与 复杂属性的名字相同(byName) - 为啥说是先 byType:如果你在bean中只保留一个class属性,可以正常运行,但是,只保留一个id属性,则会报错
- 先去容器中找 是否存在 与属性 类型一致的所有
拓展.
1、@Nullable
.
字段标记这个注解,可以为空
2、@Autowired(required = false)
.
表示允许该bean
在容器中不存在
3、@Qualifier(value="")
.
我们知道 @Autowired
是通过 在 容器中寻找 (先byType后byName)相应的bean
的,但是如果多个bean
的class
属性存在相同的,且id
与属性名不同,就会报错,那么我们就可以使用@Qualifier(value="")
配合 @Autowired
的使用 ;在让value
= “bean
中id
的值”
4、@Resource
.
与 @Autowired
相同,都是用于自动装载Bean
的(将Bean自动注入到另一个Bean中)
只不过
@Resource
默认是按byName注入,如果没有找到,就按类型找,@Autowired
是按byType注入@Resource(name="")
=@Autowired
+@Qualifier(value="")
在
jdk11
之后由于移除了javax的扩展
所以不能使用@Resource
,但是可以导入依赖<dependency> <groupId>javax.annotation</groupId> <artifactId>javax.annotation-api</artifactId> <version>1.3.2</version> </dependency>