一文吃透 Spring 中的IOC和DI(二)

✅作者简介:2022年博客新星 第八。热爱国学的Java后端开发者,修心和技术同步精进。
🍎个人主页:Java Fans的博客
🍊个人信条:不迁怒,不贰过。小知识,大智慧。
💞当前专栏:SSM 框架从入门到精通
✨特色专栏:国学周更-心性养成之路
🥭本文内容:一文吃透 Spring 中的IOC和DI
文章目录
- 准备工作
- bean 的自动注入
- bean 的生命周期
- Bean 的作用域
- Spring 注解开发
- 1、@Component 注解
- 2、@Scope 注解
- 3、@Value 注解
- 4、@Autowired 注解
- 5、@Qualifier 注解
- 6、@Resource 注解
- 7、xml配置方式与注解方式的比较

准备工作
entity 包中的创建一个 Student 类和 Teacher 类,代码如下:
Student 类:
package cn.kgc.spring02.entity;import lombok.Data;@Data
public class Student {private String name;private Integer id;private Teacher teacher;
}
Teacher 类:
package cn.kgc.spring02.entity;import lombok.Data;@Data
public class Teacher {private String name;private Double salary;
}
创建一个测试类和一个 shouldAnswerWithTrue 测试方法:
package cn.kgc.spring02;import cn.kgc.spring02.entity.Student;
import junit.framework.TestCase;
import junit.framework.TestSuite;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;/*** 如何通过配置 或注解完成自动注入*/
public class AppTest {@Testpublic void shouldAnswerWithTrue(){ApplicationContext ac = new ClassPathXmlApplicationContext("spring-config.xml");Student student = ac.getBean("student", Student.class);System.out.println("student = " + student);}
}
bean 的自动注入
- autowire=“byType” 根据属性的类型完成自动注入
<bean id="student" class="cn.kgc.spring02.entity.Student" autowire="byType"><property name="id" value="1"></property><property name="name" value="tom"></property></bean><bean id="teacher" class="cn.kgc.spring02.entity.Teacher"><property name="name" value="jack"></property><property name="salary" value="200"></property></bean>
运行测试类中的 shouldAnswerWithTrue 方法,运行效果如下:

局限: 保证spring容器中只能有一个指定类型的bean
- autowire=“byName” 根据属性的名字完成自动注入,属性名字和哪个 bean 的 id 相等,则完成注入。测试的运行效果和上面一样。
<bean id="student" class="cn.kgc.spring02.entity.Student" autowire="byName"><property name="id" value="1"></property><property name="name" value="tom"></property></bean><bean id="teacher" class="cn.kgc.spring02.entity.Teacher"><property name="name" value="jack"></property><property name="salary" value="200"></property></bean>
bean 的生命周期
1.singleton 容器启动的时候创建对象,容器正常关闭时销毁对象
2.prototype 获取对象的时候创建对象,spring容器不负责对象的销毁
生命周期的过程:
1.调用无参创建对象
2.调用set方法初始化属性
3.调用初始化方法
4.对象创建完成,使用对象
5.关闭容器,调用销毁的方法
Bean 的作用域
在配置文件中,除了可以定义 Bean 的属性值和相互之间的依赖关系,还可以声明 Bean 的作用域。例如,如果每次获取 Bean 时,都需要一个 Bean 实例,那么应该将 Bean 的 scope 属性定义为 prototype,如果 Spring 需要每次都返回一个相同的 Bean 实例,则应将 Bean 的 scope 属性定义为 singleton。
作用域的种类
Spring 容器在初始化一个 Bean 实例时,同时会指定该实例的作用域。Spring 5 支持以下 6 种作用域。
1)singleton
默认值,单例模式,表示在 Spring 容器中只有一个 Bean 实例,Bean 以单例的方式存在。
<bean id="..." class="..." scope="singleton"/>
2)prototype
原型模式,表示每次通过 Spring 容器获取 Bean 时,容器都会创建一个 Bean 实例。
<bean id="..." class="..." scope="prototype"/>
3)request
每次 HTTP 请求,容器都会创建一个 Bean 实例。该作用域只在当前 HTTP Request 内有效。
4)session
同一个 HTTP Session 共享一个 Bean 实例,不同的 Session 使用不同的 Bean 实例。该作用域仅在当前 HTTP Session 内有效。
5)application
同一个 Web 应用共享一个 Bean 实例,该作用域在当前 ServletContext 内有效。
类似于 singleton,不同的是,singleton 表示每个 IoC 容器中仅有一个 Bean 实例,而同一个 Web 应用中可能会有多个 IoC 容器,但一个 Web 应用只会有一个 ServletContext,也可以说 application 才是 Web 应用中货真价实的单例模式。
6)websocket
websocket 的作用域是 WebSocket ,即在整个 WebSocket 中有效
Spring 注解开发
除了用 XML 配置方式进行依赖注入外,还可以使用注解直接在类中定义 Bean 实例,这样就不再需要在 Spring 配置文件中声明 Bean 实例。使用注解,除了原有 Spring 配置,还要注意以下关键步骤。
在 spring-config.xml 开启注解的包扫描
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:context="http://www.springframework.org/schema/context"xsi:schemaLocation="http://www.springframework.org/schema/beanshttp://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd"><!--开启包扫描 base-package 设置需要扫描的包 --><context:component-scan base-package="cn.kgc.spring02"></context:component-scan>
</beans>
1、@Component 注解
@Component 该注解的 value 属性用于指定该 bean 的 id 值。例如在实体类 User 上添加注解@Component(value=“user”),它的意思是创建一个 User 类的 bean 实例,bean 的 id 为 user。
@Component("user")
public class User {private String uid;private String uname;private String gender;private int age;private Company company;
//省略其他方法
}
【注意】@Component(“user”) 等同于@Component(value=“user”),即默认的属性是value,其效果等同于xml配置文件。
Spring还另外提供了3个功能与@Component等效的注解:
- @Repository 专用于对 DAO 层实现类进行注解 。
- @Service 专用于对 Service 层实现类进行注解 。
- @Controller 专用于对 Controller 类进行注解。
四个注解的功能是一样的,只是使用不同的注解可以看出层次结构
2、@Scope 注解
需要在类上使用注解@Scope,其value属性用于指定作用域,默认为singleton(单例bean)。
(1)在项目spring5的Student类中添加下面的注解。
@Scope("prototype")
@Component("student")
public class User {
//省略其他代码
}
@Scope(“prototype”)等同于@Scope(value=“prototype”),这样就设置bean的作用范围为"prototype"(原型bean)
3、@Value 注解
需要在属性上使用注解@Value,该注解的value属性用于指定要注入的值。使用该注解完成属性注入时,类中无需setter。当然,若属性有setter,则也可将其加到setter上。
@Scope("prototype")
@Component("user")
public class User { @Value("1")private String uid;@Value("李白")private String uname;@Value("男")private String gender;@Value("18")private int age;
public void show(){System.out.println("用户编号:"+uid+" 用户姓名:"+uname+"性别:"+gender+"年龄:"+age);}
//省略其他方法
}
4、@Autowired 注解
需要在域属性上使用注解@Autowired,该注解默认使用按类型自动装配Bean的方式。根据类型不能完成注入,则在根据名字完成注入, 以上两种方式都失败则抛出异常。
@Component("user")
public class User {@Value("1")private String uid;@Value("李白")private String uname;@Value("男")private String gender;@Value("18")private int age; @Autowiredprivate Company company;
//省略其他方法
}
5、@Qualifier 注解
@Qualifier的value属性用于指定要匹配的Bean的id值。
@Component("user")
public class User { //省略其他代码@Autowired(required=false)
@Qualifier("mycolleg")private Company company;
}
这时域属性company必须装配id为mycompany的bean。如果找不到会报错。
6、@Resource 注解
使用@Resource注解既可以按名称匹配Bean,也可以按类型匹配 Bean。
(1)按类型注入域属性
@Resource 注解若不带任何参数,则会按照类型进行Bean的匹配注入。
@Component("user")
public class User { //省略其他代码
@Resourceprivate Company company;
}
(2)按名称注入域属性。@Resource 注解指定其name属性,则name的值即为按照名称进行匹配的Bean的id。
@Component("user")
public class User { //省略其他代码
@Resource(name="mycompany")private Company company;
}
7、xml配置方式与注解方式的比较
注解的好处是: 配置方便,直观。
缺点: 以硬编码的方式写入到了Java代码中,其修改需要重新编译代码的。
xml配置方式的好处是: 对其所做修改,无需编译代码,只需重启服务器即可将新的配置加载。
若注解与xml同用,xml的优先级要高于注解。
码文不易,本篇文章就介绍到这里,如果想要学习更多Java系列知识,点击关注博主,博主带你零基础学习Java知识。与此同时,对于日常生活有困扰的朋友,欢迎阅读我的第四栏目:《国学周更—心性养成之路》,学习技术的同时,我们也注重了心性的养成。

相关文章:
一文吃透 Spring 中的IOC和DI(二)
✅作者简介:2022年博客新星 第八。热爱国学的Java后端开发者,修心和技术同步精进。 🍎个人主页:Java Fans的博客 🍊个人信条:不迁怒,不贰过。小知识,大智慧。 💞当前专栏…...
【期末指北】嵌入式系统——选择题(feat. ChatGPT)
作者|Rickyの水果摊 时间|2023年2月20日 基本信息 ☘️ 本博客摘录了一些 嵌入式系统 的 常见选择题,供有需求的同学们学习使用。 部分答案解析由 ChatGPT 生成,博主进行审核。 使用教材信息:《嵌入式系统设计与应…...
MyBatis-Plus——代码生成器(3.5.1+版本)
文章目录配置数据源配置(DataSource)全局配置(GlobalConfig)包配置(PackageConfig)策略配置(StrategyConfig)模板引擎配置(TemplateEngine)代码生成器测试样例…...
宁盾上榜第五版《CCSIP 2022 中国网络安全行业全景册》
2月1日,国内网络安全行业媒体Freebuf咨询正式发布《CCSIP(China Cyber Security Panorama)2022 中国网络安全行业全景册》第五版。宁盾作为国产身份安全厂商入驻身份识别和访问管理(SSO、OTP、IDaaS)及边界访问控制&am…...
【Linux系统】第七篇:Linux调试器gdb的使用
文章目录一、gdb简介二、gdb的安装三、gdb使用3.1、release和debug版本3.2、gdb基本使用命令1、启动gdb2、调试命令3、显示代码(list)4、断点命令(breakpoint)5 、变量命令(variable)6、特殊调试命令7、调用…...
Shell 特殊变量及其含义
shell是我们在linux下编写自动执行程序的常见脚本工具,通常会涉及到以下几个特殊变量,它们分别是:$#、$*、$、$?、$$。 变量含义$0当前脚本的文件名。$n(n≥1)传递给脚本或函数的参数。n 是一个数字,表示…...
LeetCode 2396. 严格回文的数字
如果一个整数 n 在 b 进制下(b 为 2 到 n - 2 之间的所有整数)对应的字符串 全部 都是 回文的 ,那么我们称这个数 n 是 严格回文 的。 给你一个整数 n ,如果 n 是 严格回文 的,请返回 true ,否则返回 fals…...
【RocketMQ】源码详解:Broker启动流程
Broker启动 入口: org.apache.rocketmq.broker.BrokerStartup#main broker的启动主要分为两部分:1.创建brokerController 2.启动brokerController。与平时进行业务开发时不同的是,这里的BrokerController相当于Broker的一个中央控制器类&…...
vue事件
1. 事件传参 <button click"clickEvt($event, 22)">点我</button>2. 事件修饰符 prevent:阻止默认事件stop:阻止事件冒泡(加到子元素)once:事件只触发一次capture:使用事件的捕获模…...
研报精选230220
目录 【行业230220国信证券】银行业行业专题:经济复苏中的优质中小银行【行业230220国信证券】汽车行业周报(2023年第7周):吉利将发布新品牌“银河” ,2022年宇通纯电动客车获欧洲销量冠军【行业230220开源证券】商贸零…...
kubernetes sd configs配置详解
1.基于Kubernetes的服务发现 kubernetes_sd_config 这个是以角色(role)来定义收集的,Kubernetes SD配置允许从Kubernetes的RESTAPI中检索scrape目标,并始终与群集状态保持同步。 凡<role>必须是endpoints,service,pod&…...
Linux查看文件的命令
目录 1、tail 2、head 3、cat 4、more 5、sed 6、less Linux查看日志的命令有多种: tail、cat、tac、head、echo等,本文只介绍几种常用的方法。 1、tail 命令格式: tail[必要参数][选择参数][文件] -f 循环读取 -q 不显示处理信息 -v 显示详细的处理信…...
如何单独清除某个网页的缓存(reload)
有时候在自己服务器上调试的时候,刷新一直不更新,样式改了也看不到,就很烦 今天教你一个方法快速清除 F12 控制台情况下右击左上角的刷新 这三个分别代表: ①正常重新加载(Ctrl R): 正常重新加载 此方法,浏览器发送请求时会…...
魔兽世界经典怀旧服务器架设教程
准备工具:MySQL服务端服务器最重要的你需要会技术、要不然都瞎扯 给你东西你也看不懂。教程开始:安装MySQL并创建数据库安装MySQL社区版,并配置SQL服务器。安装SQLyog。利用其登录,创建realmd、characters、mangos、scriptdev2数据…...
Interview系列 - 05 Java|Iterator迭代器|集合继承体系|Set List Map接口特性|List实现类区别
文章目录01. 迭代器 Iterator 是什么?02. 迭代器 Iterator 有什么特点?03. 迭代器 Iterator 怎么使用?04. 如何边遍历边移除 Collection 中的元素?05. Iterator 和 ListIterator 有什么区别?06. 数组和集合的区别&…...
LeetCode 1769. 移动所有球到每个盒子所需的最小操作数
有 n 个盒子。给你一个长度为 n 的二进制字符串 boxes ,其中 boxes[i] 的值为 ‘0’ 表示第 i 个盒子是 空 的,而 boxes[i] 的值为 ‘1’ 表示盒子里有 一个 小球。 在一步操作中,你可以将 一个 小球从某个盒子移动到一个与之相邻的盒子中。…...
MKS SKIPR V1.0船长版(Voron 2.4 R2)配置简要笔记
第一次用MKS SKIPR V1.0,设置过程中,也不知道怎么回事,跟现有的资料有些出入。首先,基本的配置调试可以参考官方的使用说明。 MKS SKIPR V1.0 使用说明书 这个说明比较简单,很多深一点的东西没有提现,不过…...
90后,转行软件测试3年,从月入7000+到月入过万,整理出的这一万字经验分享。
周一发工资了,到手12857.65,美滋滋 今年是我毕业参加工作的第3年,工资终于来到5位数了。上一家公司月薪7000,实际拿到手就6450左右,感觉今年真的是元气满满啊,工资翻倍,良好的人生开端。 想起…...
Java之关于String字符串笔试面试重点
目录 一.关于字符串的常量池 1.关于字符串产生的三种方式 2.关于字符串的常量池 3.直接赋值法和new的方式产生对象的区别 二.关于intern方法 1.情况一(已经包含) 2.情况二(已经包含) 3.情况三(未包含) 4.情况四 三.关于字符串的不可变性 1.了解字符串的不可变性 2.Str…...
mdio协议
1. 简介 MDIO接口中有特定的术语定义总线上的各种设备,驱动MDIO总线的设备被定义为站管理实体(STA),而被MDC管理的目标设备称为可被MDIO管理的设备(MMD)。 STA初始化MDIO所有的通信,同时负责驱动…...
[特殊字符] 智能合约中的数据是如何在区块链中保持一致的?
🧠 智能合约中的数据是如何在区块链中保持一致的? 为什么所有区块链节点都能得出相同结果?合约调用这么复杂,状态真能保持一致吗?本篇带你从底层视角理解“状态一致性”的真相。 一、智能合约的数据存储在哪里…...
Python:操作 Excel 折叠
💖亲爱的技术爱好者们,热烈欢迎来到 Kant2048 的博客!我是 Thomas Kant,很开心能在CSDN上与你们相遇~💖 本博客的精华专栏: 【自动化测试】 【测试经验】 【人工智能】 【Python】 Python 操作 Excel 系列 读取单元格数据按行写入设置行高和列宽自动调整行高和列宽水平…...
聊聊 Pulsar:Producer 源码解析
一、前言 Apache Pulsar 是一个企业级的开源分布式消息传递平台,以其高性能、可扩展性和存储计算分离架构在消息队列和流处理领域独树一帜。在 Pulsar 的核心架构中,Producer(生产者) 是连接客户端应用与消息队列的第一步。生产者…...
Linux简单的操作
ls ls 查看当前目录 ll 查看详细内容 ls -a 查看所有的内容 ls --help 查看方法文档 pwd pwd 查看当前路径 cd cd 转路径 cd .. 转上一级路径 cd 名 转换路径 …...
家政维修平台实战20:权限设计
目录 1 获取工人信息2 搭建工人入口3 权限判断总结 目前我们已经搭建好了基础的用户体系,主要是分成几个表,用户表我们是记录用户的基础信息,包括手机、昵称、头像。而工人和员工各有各的表。那么就有一个问题,不同的角色…...
oracle与MySQL数据库之间数据同步的技术要点
Oracle与MySQL数据库之间的数据同步是一个涉及多个技术要点的复杂任务。由于Oracle和MySQL的架构差异,它们的数据同步要求既要保持数据的准确性和一致性,又要处理好性能问题。以下是一些主要的技术要点: 数据结构差异 数据类型差异ÿ…...
dify打造数据可视化图表
一、概述 在日常工作和学习中,我们经常需要和数据打交道。无论是分析报告、项目展示,还是简单的数据洞察,一个清晰直观的图表,往往能胜过千言万语。 一款能让数据可视化变得超级简单的 MCP Server,由蚂蚁集团 AntV 团队…...
均衡后的SNRSINR
本文主要摘自参考文献中的前两篇,相关文献中经常会出现MIMO检测后的SINR不过一直没有找到相关数学推到过程,其中文献[1]中给出了相关原理在此仅做记录。 1. 系统模型 复信道模型 n t n_t nt 根发送天线, n r n_r nr 根接收天线的 MIMO 系…...
使用 SymPy 进行向量和矩阵的高级操作
在科学计算和工程领域,向量和矩阵操作是解决问题的核心技能之一。Python 的 SymPy 库提供了强大的符号计算功能,能够高效地处理向量和矩阵的各种操作。本文将深入探讨如何使用 SymPy 进行向量和矩阵的创建、合并以及维度拓展等操作,并通过具体…...
视觉slam十四讲实践部分记录——ch2、ch3
ch2 一、使用g++编译.cpp为可执行文件并运行(P30) g++ helloSLAM.cpp ./a.out运行 二、使用cmake编译 mkdir build cd build cmake .. makeCMakeCache.txt 文件仍然指向旧的目录。这表明在源代码目录中可能还存在旧的 CMakeCache.txt 文件,或者在构建过程中仍然引用了旧的路…...
