面试的时候考官问道了@Resource和@Autowired注解,过后上网查了一下,在此记录自己的心得。
spring2.5提供了基于注解(Annotation-based)的配置,我们可以通过注解的方式来完成注入依赖。在Java代码中可以使用 @Resource或者@Autowired注解方式来经行注入。虽然@Resource和@Autowired都可以来完成注入依赖,但它们之间是有区 别的。首先来看一下:
a.@Resource默认是按照名称来装配注入的,只有当找不到与名称匹配的bean才会按照类型来装配注入;
b.@Autowired默认是按照类型装配注入的,如果想按照名称来转配注入,则需要结合@Qualifier一起使用;
c.@Resource注解是由JDK提供,而@Autowired是由Spring提供;
d.@Resource和@Autowired都可以书写标注在字段或者该字段的setter方法之上;
详细分析:
①注解配置
在基于主机方式配置Spring的配置文件中,你可能会见到
<context:annotation-config/>
这样一条配置,他的作用是式地向 Spring 容器注册
AutowiredAnnotationBeanPostProcessor
CommonAnnotationBeanPostProcessor
PersistenceAnnotationBeanPostProcessor
RequiredAnnotationBeanPostProcessor
这 4 个BeanPostProcessor。
注册这4个BeanPostProcessor的作用,就是为了你的系统能够识别相应的注解。
例如:
如果你想使用@Autowired注解,那么就必须事先在 Spring 容器中声明 AutowiredAnnotationBeanPostProcessor Bean。传统声明方式如下
<bean class="org.springframework.beans.factory.annotation. AutowiredAnnotationBeanPostProcessor "/>
如果想使用@ Resource 、@ PostConstruct、@ PreDestroy等注解就必须声明CommonAnnotationBeanPostProcessor
<bean class="org.springframework.beans.factory.annotation. CommonAnnotationBeanPostProcessor"/>
如果想使用@PersistenceContext注解,就必须声明PersistenceAnnotationBeanPostProcessor的Bean。
<bean class="org.springframework.beans.factory.annotation.PersistenceAnnotationBeanPostProcessor"/>
如果想使用 @Required的注解,就必须声明RequiredAnnotationBeanPostProcessor的Bean。
同样,传统的声明方式如下:
<bean class="org.springframework.beans.factory.annotation.RequiredAnnotationBeanPostProcessor"/>
一般来说,这些注解我们还是比较常用,尤其是Antowired的注解,在自动注入的时候更是经常使用,所以如果总是需要按照传统的方式一条一条配置显得有些繁琐和没有必要,于是spring给我们提供<context:annotation-config/>的简化配置方式,自动帮你完成声明。
不过,呵呵,我们使用注解一般都会配置扫描包路径选项
<context:component-scan base-package=”XX.XX”/>
该配置项其实也包含了自动注入上述processor的功能,因此当使用 <context:component-scan/> 后,就可以将 <context:annotation-config/> 移除了。
比如:
<context:component-scan base-package="carPoolingController, carPoolingService, carPoolingDao" />
就把controller包下 service包下 dao包下的注解全部扫描了。
②使用和执行步骤
修改以上配置文件的头信息后,我们就可以在Java代码通过注解方式来注入bean,看下面代码。
@Resource可以作用于字段和函数上。当作用于字段上的时候,如果我们只是简单的这样写
@Resource
PersonDao p;
这时候spring注入p的过程是
1:先查找xml中是否有id为p的元素;
2:如果没有找到,则看是否有name性(@Resource name=“”),有则查找name;
3:否则查找PersonDao类型的元素;
@Resource可作用于set函数上。
例如:
@Resource public void setP(PersonDao p) { this.p = p; }
@Autowired注解是根据类型进行查找,比如PersonDao p,他会去xml文件里查找类型为PersonDao的元素。
总结:
@Autowire 默认按照类型装配,默认情况下它要求依赖对象必须存在如果允许为null,可以设置它required属性为false,如果我们想使用按照名称装配,可以结合@Qualifier注解一起使用;
@Resource默认按照名称装配,当找不到与名称匹配的bean才会按照类型装配,可以通过name属性指定,如果没有指定name属性,当注解标注在字段上,即默认取字段的名称作为bean名称寻找依赖对象,当注解标注在属性的setter方法上,即默认取属性名作为bean名称寻找 依赖对象。
注意:如果没有指定name属性,并且按照默认的名称仍然找不到依赖的对象时候,会回退到按照类型装配,但一旦指定了name属性,就只能按照名称 装配了。
参考贴:https://blog.csdn.net/u010746364/article/details/53419861