@Resource、@Autowired、@Qualifier区别与使用,以及bean name 的默认生成规则。

前言

一、注解区别

1. @Autowired

@Autowired 是Spring的注解。通过 byType 的方式去注入,仅有一个required属性,默认为true,默认装配规则如下:

  1. 先通过类型查找,找到只有一个则装配,找不到则抛出异常,
  2. 如果找到多个,则从中按照名字查找,找到则装配,找不到则抛出异常

当required为false时,最终找不到则忽略不装配。

2. @Qualifier

@Qualifier是Spring的注解。字面含义为合格者,按名称注入。用于装配时有多个候选bean时通过指定一个标识来解决冲突,仅有一个默认value属性,作为标识,定义bean时通过添加@Qualifier(“xxx”)指定。每一个bean都有一个自身名称标识的Qualifier。

一般当出现两个及以上bean时,不知道要注入哪个,作为@Autowired()的修饰用。

  1. 当value不指定时,这个标识为"",而不是bean的名称或者作用的属性名称。
  2. 当通过类型找到一个时,但是不匹配Qualifier指定标识,也会抛出异常(它不仅解决冲突,甚至有点矫枉过正)

3. @Resource

@Resource 是 J2EE 的注解。以通过 byNamebyType 的方式注入。

默认先按 byName的方式进行匹配,如果匹配不到,再按 byType的方式进行匹配。用与资源(通常是JNDI)的注入。 Spring对其进行了支持。

装配规则:

  1. 如果指定了name属性,则按照name查找,找到且类型匹配则装配,否则配抛出异常
  2. 如果指定了name和type属性,则按照name和type精确查找,找到则装配,找不到抛出异常
  3. 如果仅指定了type属性,则按照type查找,如果只找到一个则装配,否则抛出异常
  4. 如果name和type都没有指定,则默认按照作用的属性名字查找,找到则装配,找不到则按照类型找,找到一个则装配,找不到或者找到多个抛出异常

注意 : 如果不指定name 和 type。先按 byName (其name为 注入的自定义的名称,首字母大写的变为小写,后面为驼峰命名规则)。 如果匹配不到,再按 byType的方式进行匹配。

如果想减少对 Spring 的依赖建议使用 @Resource 方法。

二、使用三个注解

我拿我之前写的需求过来写一下,我接收三种不同的数据,需要放在三个堵塞队列中,然后再使用三个线程池去消费。我想把三个堵塞队列写在一个配置类中。如下:

BlockingQueueConfig.java

package com.uniview.airport.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;

/**
 * 三个堵塞队列,分别对应三个告警类型的传递
 */
@Configuration
public class BlockingQueueConfig {

    /**
     *  飞机开关车门
     * @return
     */
    @Bean(name = "BlockingOpenAndCloseDoor")
    public BlockingQueue getBlockingQueueOpenAndCloseDoor(){
        return new LinkedBlockingQueue(2000);
    }

    /**
     *飞机撤侨
     * @return
     */
    @Bean(name = "BlockingQueueEvacuees")
    public BlockingQueue getBlockingQueueEvacuees(){
        return new LinkedBlockingQueue(2000);
    }

    /**
     * 飞机入离位
     * @return
     */
    @Bean(name = "BlockingQueueEntryAndExit")
    public BlockingQueue getBlockingQueueEntryAndExit(){
        return new LinkedBlockingQueue(2000);
    }
}

两种实现方式

@Slf4j
@RestController
@RequestMapping("objIdentify")
public class AlarmController {
    
    /**
     *  飞机开关舱门
     */
    @Resource(name = "BlockingOpenAndCloseDoor")
    private BlockingQueue blockingOpenAndCloseDoor;

    /**
     *  飞机撤侨
     */
    @Qualifier(value = "BlockingQueueEvacuees")
    @Autowired
    private BlockingQueue blockingQueueEvacuees;

    /**
     * 飞机入离位
     */
    @Resource(name = "BlockingQueueEntryAndExit")
    private BlockingQueue blockingQueueEntryAndExit;
}

成功运行,不报错。

三、bean name默认生成规则

在SSM 或者 springboot 项目中,会用到依赖注入。其前提是将这个类配置成bean并加入到spring容器中,也就是 IOC容器。

现在一般都是用配置式和注解式来将bean装配到容器中。

一般都使用注解 @Controller 、@Service、 @Repository、@Component、@Configuration 等注解来标注在类上,一般用 @Bean 标注方法上(一般在配置类上)。

那他们的 bean name 是多少呢????

在Spring中,当我们配置一个bean的时候,可以不指定name,这样的话,Spring会生成一个默认的beanName,生成规则:原以为只是简单的将类名首字母小写,后面为驼峰命名规则,Spring官方文档还指出——当类名的首字母和第二个字母是大写的时候,将采用原始的类名作为beanName。

例如:

  1. SysConfig - sysConfig,Tools - tools。
  2. RBACUserLog - RBACUserLog,RBACUser - RBACUser,RBACRole - RBACRole。

spring文档原文如下:

With component scanning in the classpath, Spring generates bean names for unnamed components, following the rules above: essentially, taking the simple class name and turning its initial character to lower-case. However, in the (unusual) special case when there is more than one character and both the first and second characters are upper case, the original casing gets preserved. These are the same rules as defined by java.beans.Introspector.decapitalize (which Spring is using here).

大概意思就是说spring在给未命名的组件生成bean name的时候,采用简单的类名并将其初始字符转换为小写。但在特殊情况下,当第一个和第二个字符都是大写的时候,保留原始的形式。而spring使用的就是在java.beans.Introspector类中的decapitalize方法实现的。

Bean注解括号里面的字符串就是bean的名字,也可以不加,默认bean的名字是@Bean注解所对应的方法的方法名

  • 8
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
### 回答1: @Resource注解是Java中的一种注解,它可以用来标记一个属性、方法或构造函数,告诉容器在进行自动装配时,使用名称或类型来查找需要注入的bean。 @Autowired注解是Spring框架中的一种注解,它可以用来标记一个属性、方法或构造函数,告诉容器在进行自动装配时,使用类型来查找需要注入的bean。 ### 回答2: @resource注解和@Autowired注解都是用于在Spring框架中进行依赖注入的方式。 @resource注解是JSR 250规范中的一部分,它可以用来标记一个类的属性或方法来指示Spring容器注入一个特定的资源。可以应用在字段上,在setter方法上,以及在构造函数中,用来注入具体类型的依赖。它可以使用一个name属性来指定要注入的资源的名称,如果没有指定name属性,它将根据变量的名称来查找匹配的资源。@resource注解可以用于注入任何类型的资源,包括其他对象、数据源、事务管理器等。 @Autowired注解是Spring框架提供的一种依赖注入方式。它可以通过类型来自动注入一个合适的bean或者其他的依赖项。可以应用在字段上,setter方法上,以及构造函数中。与@resource注解不同的是,@Autowired注解不需要明确指定需要注入的bean的名称,它会根据类型来自动寻找匹配的bean,并将其注入到对应的属性中。如果存在多个相同类型的bean,可以使用@Qualifier注解来指定要注入的bean的名称。在进行注入时,Spring会根据属性的类型,从容器中查找匹配的bean,并将其自动装配到指定的属性中。 总结来说,@resource注解主要用于注入各种类型的资源,可以指定资源的名称,而@Autowired注解主要用于自动注入其他对象或者依赖项,根据类型自动寻找匹配的bean进行注入。 ### 回答3: @Resource注解和@Autowired注解都是Spring框架中用于进行依赖注入的注解。 @Resource注解是JavaEE的注解,可以用于引用其他组件或者资源。在Spring中,它可以用于注入依赖的组件。@Resource注解有两个常用的属性:name和type。name属性可以指定要注入的组件的名称,type属性可以指定要注入的组件的类型。如果两个属性都没有指定,则根据属性的类型进行自动装配。 @Autowired注解是Spring框架提供的注解,用于进行自动装配。它可以根据属性的类型进行自动装配,也可以根据属性的名称进行自动装配。当需要装配的组件只有一个时,会根据类型进行匹配。当需要装配的组件有多个时,会根据属性名称进行匹配。如果找不到匹配的组件,会抛出异常。 在使用@Resource注解时,可以使用@Resource和@Autowired注解的效果是一样的,但是@Resource注解的功能更加强大,可以引用其他JavaEE容器的资源,而@Autowired注解只能引用Spring容器中的组件。 总结起来,@Resource注解是JavaEE的注解,用于引用其他组件或资源,而@Autowired是Spring框架的注解,用于进行自动装配。在Spring中,可以使用@Resource和@Autowired注解来实现依赖注入的功能。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

java冯坚持

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值