当前位置:网站首页>第4章 Bean对象的作用域以及生命周期
第4章 Bean对象的作用域以及生命周期
2022-07-27 04:18:00 【沉睡羊sleepysheep】
4-1 bean scope属性讲解

代表我们的bean在容器中是允许存在多个实例的

前两个需要重点掌握

为什么spring会默认的使用单例模式呢?
原因很简单,如果每一次在需要某个对象的时候都去创建它,会额外占用内存的空间,创建对象的时候也要额外占用cpu的计算资源,频繁创建对象所带来的资源损耗再小应用中还可以忽略不计但是bat这样级别的公司中动不动几十万用户同时访问那这个资源上的损失就必须考虑在内,而ioc单例模式可以有效的解决创建对象时占用资源的问题,因为全局只用创建一次就可以了,但这样也会衍生出一个新的问题。
我现在只有一个对象三个对象同时发起调用操作会不会出现阻塞的问题呢?其实不会的

什么是线程安全问题?又是怎样体现出来的呢?

多线程的话

这时就会出现设置的是1出现的是2这种问题,和预期不符自然程序就会出bug。
如何解决?
为每一个用户都分配一个只属于他自己的对象,个操作各的互不影响
这种创建多个对象的设置放在springioc中就称作prototype多例

在每一次产生对象注入或者通过getBean获取userDao的过程中,由ioc容器都会创建新的实例,也就意味着产生关联以后b1拥有与之对应的独立的dao。每个线程的工作都互不影响
执行效率相对较低![]()

4-2 bean scope的实际应用
创建新工程

创建用户dao
增加默认构造方法

默认为单例模式

单例模式有一个特点就是在ioc初始化的过程中就会将这个对象进行创建
验证一下
运行


参照一下多列

没有输出
用一个对象来保存
在调用getBean的时候产生了新对象

多放几个

从这里就能了解单列和多列表现上的区别了
内容再延伸一下


打开xml进行配置

在UserService上也增加构造方法

当前配置在ioc容器初始化的过程中会产生几个对象呢?
答案是两个
因为使用的是单列所以当然会创建userService对象,除此以外又去引用了
![]()
这个对象 而userDao在文件初始化的过程中是不存在的,于是ioc容器也同样userDao的实例化
运行
![]()

默认情况下bean的顺序是按照书写的顺序创建的,但是在实际运行中为什么是userService先创建?清除prototype

为什么取消顺序正确了呢
增加prototype后第一个bean是不会在ioc容器初始化的时候自动的实例化,在实例化UserService的过程中ioc容器他需要一个userDao的实例,于是他再去创建userDao对象,也就是说当我们的某一个属性去关联到一个多例对象的时候,同样会触发实例化对象的操作

都加上prototype


在绝大多数场景下dao类service类乃至后面学习的springmvc的控制器类都是单例的。如果一个属性是恒定不变的就可以使用单例如果不断地变化就要使用多例了
4-4 对象生命周期

通过案例来说明

创建订单属性


回到xml进行配置

难道要手动计算出价钱吗?我们要让程序计算在哪儿算呢?

这样做没错但是调用一次就要进行一次运算
增加init方法


利用了init-method是在设置完属性以后再去执行的特点来完成了total属性的计算
为了让程序运行看起来更加清晰,我们将对象创建和设置属性的每一个步骤都打印一些文本



![]()
![]()
运行

在销毁时对资源进行释放,该怎么做呢?
![]()
增加用于销毁ioc容器的方法,该方法并没在applicationContext这个接口中进行定义而是放在了classPathXmlapplicationContext这个具体的实现类中,因此在调用方法的时候由idea自动为我们转换回具体的实现类
销毁容器的过程中会自动调用我们在bean中设置的
方法

资源指的是什么?其实在程序运行过程中这些资源,可以是一个文件,也可以是一个网络的连接,甚至还可以是其他系统的调用,这些都被称为资源,而在destory中我们就要将这些资源释放掉,
运行一下

4-5 实现极简IoC容器
创建工程

创建类


创建配置文件

这个文件是如何在运行时创建对象的呢?我们需要自己实现ioc容器
创建接口
![]()

模拟spring的applicationContext接口

getBean是从ioc容器中将对应的Bean进行提取

这个类就是实现接口并完成ioc容器的创建过程
![]()
创建一个hashMap作为一个ioc容器,之后的工作就是在实例化classPathXmlApplicationContext对象过程中去加载处理xml配置文件了
创建默认构造方法,去读取刚才编写的xml文件

![]()
通过getPath得到文件的路径
如果包含中文可能会找不到,进行解码
![]()
获取到路径后如何进行解析呢?
引入组件


回到代码,利用方法读取解析把xml放到document中

后面的工作就是按照xml的格式依次读取
![]()
将当前根节点下所有bean标签进行获取
利用for循环遍历集合,在遍历过程中每一个elements都包含了两个属性一个id一个class,我们需要读取出来

使用反射技术forName方法加载className得到与之对应的类对象,调用newInstance调用默认构造方法创建apple类的实例

至此apple这个对象就已经被创建好了
利用
![]()
这样就相当于ioc容器对刚才新创建的对象赋予了beanId进行管理,到此作为ioc容器创建对象的职责就完成了

对指定的beanId提取并进行返回

测试一下

完成ioc容器的初始化工作,与此同时ioc容器中便会创造出一个beanId为sweetApple的apple对象

如何验证呢,打印出ioc容器中的对象
![]()
可以在应用入口获取新创建的对象


从使用的角度来说,和我们利用SpringIoc容器进行代码初始化的过程是几乎一样的
还需要在ioc容器中继续通过set方法进行属性注入
![]()
在这个properties集合中其实就包括了

这三个属性
利用for循环进行遍历,强制类型转换,提取属性

获取到以后如何在运行时动态注入呢?
基于property完成数据注入是通过set方法来完成的
而set方法命名的格式为set+首字母大写属性名

如何通过方法名来完成调用呢?
![]()
![]()
运行一下


边栏推荐
- Eureka service registry
- Preliminary understanding of NiO
- 安全第四次课后练习
- 结构型模式-装饰者模式
- Wechat applet rotation map
- Scala immutable map, variable map, map conversion to other data types
- Spark practice case (upgraded version)
- 微服务的feign调用header头被丢弃两种解决方案(附源码)
- BigDecimal pit summary & Best Practices
- Cloudcompare & PCL match point distance suppression
猜你喜欢

2022-07-26:以下go语言代码输出什么?A:5;B:hello;C:编译错误;D:运行错误。 package main import ( “fmt“ ) type integer in

Dino paper accuracy, and analyze the variant of its model structure & Detr

Detailed explanation of TCP protocol knowledge

无有线网络下安装并配置debian

干货 | 独立站运营怎么提高在线聊天客户服务?

Plato farm has a new way of playing, and the arbitrage eplato has secured super high returns

结构型模式-适配器模式

管理信息系统期末复习

可视化领域 SVG

安全第四次课后练习
随机推荐
[day02] Introduction to data type conversion, operators and methods
Prometheus Node Exporter 常用监控指标
Some common instructions in JVM tuning
People don't talk much, engineers don't talk much
Using webmvcconfigurer to intercept interface requests is being enhanced (with source code)
grid布局
Shell的正则表达式入门、常规匹配、特殊字符:^、$、.、*、字符区间(中括号):[ ]、特殊字符:\、匹配手机号
数据分析师岗位分析
EVT interface definition file of spicy
网工知识角|只需四个步骤,教会你使用SecureCRT连接到eNSP,常用工具操作指南必看
Plato farm has a new way of playing, and the arbitrage eplato has secured super high returns
els 兼容性DC、传递图片到窗口
Brightcove任命Dan Freund为首席营收官
shell编程增强
timestamp列使用varchar类型和使用date类型有什么区别?
深度剖析 —— 动态内存管理
Sed output specified line
法解析的外部符号 “public: virtual __cdecl nvinfer1::YoloLayerPlugin::~YoloLayerPlugin(void)“ “public: virtua
Session&Cookie&token
干货 | 独立站运营怎么提高在线聊天客户服务?