@Autowired
内容目录

@Autowired

概念

@Autowired 是Spring框架提供的注解,用于实现依赖注入。

它根据类型驱动,类型自动匹配并注入Bean。

Spring容器负责在运行时解析 @Autowired 注解,自动将依赖的Bean注入到需要它们的组件中。

此注解可以应用于字段、方法和构造函数上,支持通过类型匹配、限定符(如 @Qualifier )以及按名称匹配等多种策略来确定具体的依赖项。

通俗说法

想象一下,你开了一家面包店,每天需要一定量的面粉来制作面包。@Autowired 就像是一个自动化的供应链系统,它知道你店里需要面粉,不需要你亲自跑到市场挑选,而是自动帮你把面粉送到厨房里。这样,你只需要告诉系统“我需要面粉”,剩下的事情系统会帮你搞定。

比如,你的面包店有一个做面团的机器(一个类),这个机器需要面粉(另一个类的服务)。使用 @Autowired 就像给这个机器贴了一个标签,写着“请自动给我送面粉来”。Spring框架就像是看懂这个标签的配送员,会在面包店开门(应用启动)前,确保面粉已经放在机器旁边了。

同时你还可以使用 @Qualifier 注解限定名称匹配,就像在标签写“我需要的是低筋小麦面粉” 。

所属

Spring框架。

import org.springframework.beans.factory.annotation.Autowired;

作用

自动装配Bean,减少XML配置或显式setter方法调用。

它可以在类的构造函数、成员变量、setter方法和方法参数上使用。

用法

  • 字段注入:
    @Autowired 
    private MyService myService;
  • 构造器注入:
    public MyClass(@Autowired MyService myService) {
        this.myService = myService;
    }
  • setter(方法)注入:
    @Autowired 
    public void setMyService(MyService myService) {
        this.myService = myService;
    }

使用场景

适合于当依赖关系明确且单一,或者需要确保依赖项在对象创建时就完全初始化的场景。

对比 @Resource 使用这两个注解的优缺点

@Autowired

优点:

  • 类型驱动,简化配置,通常只需关注类型匹配即可。
  • 支持构造器、字段、方法和参数级别的注入,使用灵活。
  • 强制依赖项的存在,有助于设计更健壮的代码结构。

缺点:

  • 默认情况下不支持名称匹配,当有多个相同类型的Bean时可能造成歧义。
  • 隐藏了依赖关系,不如构造器注入明显,可能降低代码可读性。
  • 测试时,需要模拟依赖时可能较为繁琐。

@Resource

优点:

  • 支持名称匹配,提供了额外的灵活性,特别适合于解决依赖冲突或需要特定命名约定的情况。
  • 由于是Java EE标准,因此具有更好的跨框架兼容性。
  • 可以通过指定name属性精确控制注入的Bean。

缺点:

  • 默认按名称匹配,可能导致在未明确指定名称时,依赖注入的意图不如类型驱动明确。
  • 默认required属性为false,意味着如果没有匹配的Bean,该注解会被忽略,这可能引入潜在的错误或混淆。
  • 不如 @Autowired 那样广泛集成于Spring框架的其他特性中,可能在一些高级功能上支持不足。

举例说明“类型驱动”和“名称匹配”

1. 类型驱动

类型驱动匹配就像是在咖啡店点咖啡,你说:“我要一杯拿铁。”

无论哪位咖啡师在吧台,只要你点的是拿铁,他们都知道怎么制作,你不在乎是哪一位咖啡师为你服务,你在乎的是得到一杯拿铁。

这里的“拿铁”就是类型,你依靠类型来获得想要的产品,而不关心具体的提供者是谁。

代码演示

想象我们有两个实现了相同接口的Service类,分别是 EmailServiceSmsService ,而我们的 Controller 需要注入一个实现该接口的服务。

public interface MessageService {
    void sendMessage(String message);
}

@Service("emailService")
public class EmailServiceImpl implements MessageService {
    // 实现细节
}

@Service("smsService")
public class SmsServiceImpl implements MessageService {
    // 实现细节
}

@Controller
public class MessageController {
    @Autowired
    private MessageService messageService; // 类型驱动注入,Spring会根据类型找到一个合适的MessageService Bean注入
}

在这个例子中,Spring会自动根据类型 MessageService 找到一个合适的Bean注入到 messageService 字段。

假设没有特别配置,默认情况下如果没有指定名字且只有一个实现类,Spring会自动注入。如果有多个实现类且没有指定名字,可能会抛出异常或需要进一步的配置来解决歧义。

2. 名称匹配

名称匹配则像是在餐厅预订座位,你说:“我想预订靠窗有风景的‘1号桌’。”

这里,“1号桌”是特定的名称,你指定了一个具体的位置,而不是说“我想要一张桌子”。餐厅会根据这个名字找到那个特定序号的、有风景观赏优势的桌子给你预留,而不是随便安排一张桌子。

代码演示

如果我们希望在 MessageController 中明确指定使用哪个实现类,可以使用 @Qualifier 注解配合 @Autowired

@Controller
public class MessageController {
    @Autowired
    @Qualifier("emailService") // 名称匹配,指定注入名为emailService的Bean
    private MessageService messageService;
}

或者使用 @Resource 注解实现名称匹配,你可以直接在注解中指定Bean的名称。

@Controller
public class MessageController {
    @Resource(name = "emailService") // 名称匹配,指定注入名为emailService的Bean
    private MessageService messageService;
}

在这个例子中,@Resource 注解取代了 @Autowired + @Qualifier 的组合。

通过在 @Resource 注解中添加 name 属性并设置为 "emailService" ,我们指定了要注入的Bean的名称,实现了与之前使用 @Qualifier 相同的功能。 @Resource 注解源自Java EE规范,它允许根据名称或按类型(默认行为)进行注入,当指定了 name 属性时,它就按照名称匹配的方式工作。

版权声明:本文《@Autowired》是由陶其原创撰写,首发于陶其的个人博客
转载声明:如需转载本文,请务必在转载处保留原文链接:https://www.tqazy.com/?p=96,并明确注明文章来源。
暂无评论

发送评论 编辑评论

|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇