使用注解实现自动装配
前言
jdk1.5开始支持注解,spring2.5开始支持注解
要是使用注解须知(bean的id要和实体类的属性名一样)
使用
导入约束(context约束)
<context:annotation-config/>
配置注解支持
<?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
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd
">
<!--开启注解支持-->
<context:annotation-config/>
</beans>
修改掉原本的xml
<bean id="cat" class="com.cjh.pojo.Cat"/>
<bean id="dog" class="com.cjh.pojo.Dog"/>
<bean id="people" class="com.cjh.pojo.People"/>
完整的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
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd
">
<!--开启注解支持-->
<context:annotation-config/>
<bean id="cat" class="com.cjh.pojo.Cat"/>
<bean id="dog" class="com.cjh.pojo.Dog"/>
<bean id="people" class="com.cjh.pojo.People"/>
</bean>
</beans>
给实体类的字段上加上注解
People
package com.cjh.pojo;
import org.springframework.beans.factory.annotation.Autowired;
public class People {
@Autowired
private Cat cat;
@Autowired
private Dog dog;
private String name;
public Cat getCat() {
return cat;
}
public Dog getDog() {
return dog;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "People{" +
"cat=" + cat +
", dog=" + dog +
", name='" + name + '\'' +
'}';
}
}
测试
import com.cjh.pojo.People;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class MyTest {
@Test
public void test1(){
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
People people = context.getBean("people",People.class);
people.getCat().shout();
people.getDog().shout();
System.out.println(people);
}
}
结果
在set上使用也可以
@Autowired
public void setCat(Cat cat) {
this.cat = cat;
}
科普
@Nullable
@Nullable 字段标记了这个注解,说明这个字段可以为null
例如这里,在构造器中加上@Nullable,这样就不会报空指针异常了
public People(@Nullable String name) {
this.name = name;
}
@Autowired
如何使用@Autowired来设置字段为null?
public @interface Autowired {
boolean required() default true;
}
只需要设置他的required的false
就可以,默认为true
//如果显示定义了Autowired的required属性为false,说明这个对象可以为null,否则不允许为空
@Autowired(required = false)
复杂情况
如果@Autowired自动装配环境比较复杂,自动装配无法通过一个注解的时候呢?
解决1
你可以加一个@Qualifier (value=“xxxx”) 两者配合使用
这样你就可以用其他的bean了。
源码:
public @interface Qualifier {
String value() default "";
}
使用:
@Autowired
@Qualifier("dog222")
beans.xml
<bean id="cat" class="com.cjh.pojo.Cat"/>
<bean id="dog" class="com.cjh.pojo.Dog"/>
<bean id="dog222" class="com.cjh.pojo.Dog"/>
解决2
@Resource
这个装配不需要spring,也可以用
他会先通过bean的id来查找,找不到就去找包名,最后找不到才报错
前提是不能多个有重复的内容,必须唯一的bean
使用:
@Resource
private Cat cat;
@Resource(name="dog222")
private Dog dog;
小结
@Resource和@Autowired的区别:
都是用来自动装配的,都可以放在属性字段上
@Autowired通过byType
的方式来实现,而且必须要求这个对象必须存在
@Resource默认通过byname
的方式来实现,如果找不到名字,通过bytype实现。如果两个都找不到的情况下,就报错!
执行顺序不同