目录
一、@Autowired注解
@Autowired是根据类型注入,也就是常说的按byType 注入。
1. 常见用法
@Service
public class User {
public String sayHello(){
return "hello";
}
}
使用@Autowired注入User ,首先会根据类型去寻找类型是User的类并注入been,也就是注入上面的User 的实例,如果没有找到再根据名字user 去寻找。
public class UserConsumer {
@Autowired
User user ;
public void findStudentsTeach(String name) {
//hello
System.out.println(user.sayHello());
}
}
2.当有多个实现类时
如下,UserDaoImplOne 和UserDaoImplTwo 都实现了 UserDao 接口。
public interface UserDao {
public String sayHello();
}
@Service
public class UserDaoImplOne implements UserDao {
@Override
public String sayHello(){
return "aaaaaa,hello";
}
}
@Service
public class UserDaoImplTwo implements UserDao {
@Override
public String sayHello(){
return "bbbbb,hello";
}
}
此时,如果你像下面这样写会报错 required a single bean, but 2 were found:
public class UserConsumer {
@Autowired
UserDao userDao;
public void findStudentsTeach(String name) {
//编译不通过会报错
System.out.println(user.sayHello());
}
}
因为@Autowired是按类型来注入的,你注入的类型是UserDao ,而UserDaoImplOne 和UserDaoImplTwo 的类型都是UserDao ,所以它不知道你要的是哪一个,所以它分分钟死给你看。
正确的注入有以下几种方式,
多个实现类注入,方式一:
用哪个就注入哪个的名称,首字母小写。
public class UserConsumer {
@Autowired
UserDao userDaoImplOne;
public void findStudentsTeach(String name) {
//aaaaaa,hello
System.out.println(userDaoImplOne.sayHello());
}
}
UserDaoImplOne 和UserDaoImplTwo 的类型都是UserDao ,如果你想注入UserDaoImplOne可以用 userDaoImplOne 指定(首字母小写)。因为@Autowired 首先是根据类型UserDao 来查找,发现有两个实现类,它不知道要注入哪个,所以会进一步判断名称,如果有对应的名称就注入名称,如果没找到名称都就报错。
多个实现类注入,方式二:
使用@Qualifier注解指定要注入哪一个been。
public class UserConsumer {
@Autowired
@Qualifier("userDaoImplOne")
UserDao abc;
public void findStudentsTeach(String name) {
//aaaaaa,hello
System.out.println(abc.sayHello());
}
}
这种方式和方式一有点类似。
区别方式一里我们不能自定义变量名称,只能使用userDaoImplOne、或userDaoImplTwo;
而方式二里我们可以给注入的been随便起名字,比如我们起的abc。
多个实现类注入,方式三:
使用@Service指定名称。相当于给UserDaoImplOne 起个别名
@Service("abc")
public class UserDaoImplOne implements UserDao {
@Override
public String sayHello(){
return "aaaaaa,hello";
}
}
现在要 注入UserDaoImplOne的时候就要用 abc 这个名。
public class UserConsumer {
@Autowired
UserDao abc;
public void findStudentsTeach(String name) {
//aaaaaa,hello
System.out.println(abc.sayHello());
}
}
@Autowired 总结:
1.一个接口只有一个实现的情况下,属性名字怎么写都无所谓,因为按照类型匹配就只有一个bean
2.一个接口多个实现的情况下:
-
(1)属性名字跟组件名字不一致,组件名字可以指定为组件的类名,首字母要小写,比如:UserDao userDaoImplOne 或 UserDao userDaoImplTwo
-
(2)属性名字跟组件名字不一致,配合@Qualifier 注解指定组件名字
-
(3) 属性名字跟组件名字一致,组件名字可以在声明的时候指定,比如 @Service(“abc”)
二、@Resource注解
@Resource是根据名字注入,也就是常说的按byName注入。
1. 常见用法
@Service
public class User {
public String sayHello(){
return "hello";
}
}
使用@Resource注入User ,首先会去寻找名字是user 的been注入,也就是注入上面的User 的叫user 的实例,如果没有找到再按照类型去找。
public class UserConsumer {
@Resource
User user ;
public void findStudentsTeach(String name) {
//hello
System.out.println(user.sayHello());
}
}
2.当有多个实现类时
用法和上面@Autowired 的一样。通过名字、@Qualifier、@Service(“xxx”)三种方式使用。