首页 > 其他分享 >Spring 基础总结

Spring 基础总结

时间:2022-11-12 08:55:29浏览次数:40  
标签:总结 Resource Spring 基础 bean Bean 注解 IoC

title: Spring 基础总结
date: 2022-11-01 09:47:12
tags:
- Spring

Spring IoC

谈谈自己对于 Spring IoC 的了解

IoC(Inverse of Control:控制反转) 是一种设计思想,而不是一个具体的技术实现。IoC 的思想就是将原本在程序中手动创建对象的控制权,交由 Spring 框架来管理。不过, IoC 并非 Spring 特有,在其他语言中也有应用。

为什么叫控制反转?

  • 控制 :指的是对象创建(实例化、管理)的权力
  • 反转 :控制权交给外部环境(Spring 框架、IoC 容器)

将对象之间的相互依赖关系交给 IoC 容器来管理,并由 IoC 容器完成对象的注入。这样可以很大程度上简化应用的开发,把应用从复杂的依赖关系中解放出来。 IoC 容器就像是一个工厂一样,当我们需要创建一个对象的时候,只需要配置好配置文件/注解即可,完全不用考虑对象是如何被创建出来的。

在实际项目中一个 Service 类可能依赖了很多其他的类,假如我们需要实例化这个 Service,你可能要每次都要搞清这个 Service 所有底层类的构造函数,这可能会把人逼疯。如果利用 IoC 的话,你只需要配置好,然后在需要的地方引用就行了,这大大增加了项目的可维护性且降低了开发难度。

在 Spring 中, IoC 容器是 Spring 用来实现 IoC 的载体, IoC 容器实际上就是个 Map(key,value),Map 中存放的是各种对象。

Spring 时代我们一般通过 XML 文件来配置 Bean,后来开发人员觉得 XML 文件来配置不太好,于是 SpringBoot 注解配置就慢慢开始流行起来。

什么是 Spring Bean?

简单来说,Bean 代指的就是那些被 IoC 容器所管理的对象

我们需要告诉 IoC 容器帮助我们管理哪些对象,这个是通过配置元数据来定义的。配置元数据可以是 XML 文件、注解或者 Java 配置类。

<!-- Constructor-arg with 'value' attribute -->
<bean id="..." class="...">
   <constructor-arg value="..."/>
</bean>

下图简单地展示了 IoC 容器如何使用配置元数据来管理对象。

img

org.springframework.beansorg.springframework.context 这两个包是 IoC 实现的基础,如果想要研究 IoC 相关的源码的话,可以去看看

将一个类声明为 Bean 的注解有哪些?

  • @Component :通用的注解,可标注任意类为 Spring 组件。如果一个 Bean 不知道属于哪个层,可以使用 @Component 注解标注。
  • @Repository : 对应持久层即Dao层,主要用于数据库相关操作。
  • @Service : 对应服务层,主要涉及一些复杂的逻辑,需要用到 Dao 层。
  • @Controller : 对应 Spring MVC 控制层,主要用户接受用户请求并调用 Service 层返回数据给前端页面。

@Component 和 @Bean 的区别是什么?

@Component 和 @Bean 是两种使用注解来定义bean的方式。

  • @Component 注解作用于,而@Bean注解作用于方法

  • @Component 通常是通过类路径扫描来自动检测 以及自动装配bean到 Spring 容器中,注释类和bean之间存在隐式的一对一映射(即每个类一个bean)。这种方法对需要进行逻辑处理的控制非常有限,因为它纯粹是声明性的。(可以使用 @ComponentScan 注解定义要扫描的路径从中找出标识了需要装配的类自动装配到 Spring 的 bean 容器中)。

    @Bean 注解通常是我们在标有该注解的方法中定义产生这个 bean,@Bean告诉了 Spring 这是某个类的实例,当我需要用它的时候还给我。

  • @Bean 注解比 @Component 注解的自定义性更强,而且很多地方我们只能通过 @Bean 注解来注册 bean。比如当我们引用第三方库中的类需要装配到 Spring容器时,又没有没有源代码,也就没办法使用 @Component 进行自动配置,则只能通过 @Bean来实现。不过同样的也可以通过xml方式来定义。

@Bean注解使用示例:

@Configuration
public class AppConfig {
    @Bean
    public TransferService transferService() {
        return new TransferServiceImpl();
    }
}

上面的代码相当于下面的 xml 配置

<beans>
    <bean id="transferService" class="com.acme.TransferServiceImpl"/>
</beans>

下面这个例子是通过 @Component 无法实现的。

@Bean
public OneService getService(status) {
    case (status)  {
        when 1:
            return new serviceImpl1();
        when 2:
            return new serviceImpl2();
        when 3:
            return new serviceImpl3();
    }
}

注入 Bean 的注解有哪些?

Spring 内置的 @Autowired 以及 JDK 内置的 @Resource@Inject 都可以用于注入 Bean。

Annotaion Package Source
@Autowired org.springframework.bean.factory Spring 2.5+
@Resource javax.annotation Java JSR-250
@Inject javax.inject Java JSR-330

@Autowired@Resource使用的比较多一些。

@Autowired 和 @Resource 的区别是什么?

@Autowired

先byType,满足多个条件时,变为byName

Autowired 属于 Spring 内置的注解,默认的注入方式为byType(根据类型进行匹配),也就是说会优先根据接口类型去匹配并注入 Bean (接口的实现类)。

这会有什么问题呢? 当一个接口存在多个实现类的话,byType这种方式就无法正确注入对象了,因为这个时候 Spring 会同时找到多个满足条件的选择,默认情况下它自己不知道选择哪一个。

这种情况下,注入方式会变为 byName(根据名称进行匹配),这个名称通常就是类名(首字母小写)。就比如说下面代码中的 smsService 就是我这里所说的名称,这样应该比较好理解了吧。

// smsService 就是我们上面所说的名称
@Autowired
private SmsService smsService;

举个例子,SmsService 接口有两个实现类: SmsServiceImpl1SmsServiceImpl2,且它们都已经被 Spring 容器所管理。

// 报错,byName 和 byType 都无法匹配到 bean
@Autowired
private SmsService smsService;
// 正确注入 SmsServiceImpl1 对象对应的 bean
@Autowired
private SmsService smsServiceImpl1;
// 正确注入  SmsServiceImpl1 对象对应的 bean
// smsServiceImpl1 就是我们上面所说的名称
@Autowired
@Qualifier(value = "smsServiceImpl1")
private SmsService smsService;

我们还是建议通过 @Qualifier 注解来显示指定名称而不是依赖变量的名称。

@Resource

先byName,满足多个条件时,变为byType

@Resource属于 JDK 提供的注解,默认注入方式为 byName。如果无法通过名称匹配到对应的 Bean 的话,注入方式会变为byType

@Resource 有两个比较重要且日常开发常用的属性:name(名称)、type(类型)。

public @interface Resource {
    String name() default "";
    Class<?> type() default Object.class;
}

如果仅指定 name 属性则注入方式为byName,如果仅指定type属性则注入方式为byType,如果同时指定nametype属性(不建议这么做)则注入方式为byType+byName

// 报错,byName 和 byType 都无法匹配到 bean
@Resource
private SmsService smsService;
// 正确注入 SmsServiceImpl1 对象对应的 bean
@Resource
private SmsService smsServiceImpl1;
// 正确注入 SmsServiceImpl1 对象对应的 bean(比较推荐这种方式)
@Resource(name = "smsServiceImpl1")
private SmsService smsService;

简单总结一下:

  • @Autowired 是 Spring 提供的注解,@Resource 是 JDK 提供的注解。
  • Autowired 默认的注入方式为byType(根据类型进行匹配),@Resource默认注入方式为 byName(根据名称进行匹配)。
  • 当一个接口存在多个实现类的情况下,@Autowired@Resource都需要通过名称才能正确匹配到对应的 Bean。Autowired 可以通过 @Qualifier 注解来显示指定名称,@Resource可以通过 name 属性来显示指定名称。

标签:总结,Resource,Spring,基础,bean,Bean,注解,IoC
From: https://www.cnblogs.com/stdxiaozhang/p/16882666.html

相关文章

  • 【转载】Springboot2.x Lombok之@Builder注解
    转载:https://www.cnblogs.com/MrYuChen-Blog/p/13993196.html使用过程中遇到dto类提示没有默认构造参数的问题,可以给类加上@AllArgsConstructor与@NoArgsConstructor......
  • 一个工作流的项目的经验总结
    最近做了一个关于工作流的定制化开发,添加会签和或签的功能,做的比较辛苦,回头总结了一些经验。1  高度定制化工作流项目的选择框架要谨慎,慎重,再慎重!原有的框架不是为你......
  • SpringMVC
    SpringMVC:学习视频-狂神说SpringMVC:视频链接SpringMVCssm:mybatis+Spring+SpringMVCMVC三层架构JavaSE:认真学习,老师带,入门快!JavaWeb:认真学习,老师带,入门快!......
  • Spring —— AOP(面向切面编程)
    AOP(AspectOrientedProgramming)简介面向切面编程,一种编程范式,指导开发者如何组织程序结构作用:在不惊动原始设计的基础上为其进行功能增强Spring理念:无入侵式/无侵入式......
  • 第三周总结
    WEEK8WEEK9CONCLUSION1CONCLUSION2......
  • Linux基础——根目录扩容
    1、准备扩容/dev/mapper/centos-root[root@ceph-admin~]#df-ThFilesystem              Type      Size  UsedAvailUse%Mountedondevtmpf......
  • Linux基础——内核排查过程
    根因:(内核BUG)BUG:unabletohandlekernelNULLpointerdereferenceat0000000000000019,代码调用函数assign_irq_vector报错,通过升级内核版本进行修复。解决办法:  ......
  • Spring 事务扩展及分布式事务可见性问题
      大家注意点,这个@Transactional其实在两种情况下会失效的:第一种就是:在方法内调用的时候,因为它没有经过Bean的代理,所以它没办法依赖Spring的AOP增强去进行事务的控......
  • 【SpringBoot 技术专题】「开发实战系列」Undertow web容器的入门实战及调优方案精讲
    Undertowweb容器Undertow介绍Undertow是红帽公司开发的一款基于NIO的高性能Web嵌入式服务器,红帽公司(RedHat)的开源产品,且是WildFly8(JBoss)默认的Web服务器.;官网API......
  • 简单进行Springboot Beans归属模块单元的统计分析方法
    简单进行SpringbootBeans归属模块单元的统计分析方法背景基于Springboot的产品变的复杂之后启动速度会越来越慢.公司同事得出一个结论.beans数量过多会导致启动速......