Java多线程编程核心技术-第6章-单例模式与多线程-读书笔记
第 6 章 单例模式与多线程
本章主要内容
如何使单例模式遇到多线程是安全的、正确的。
6.1 立即加载 / “饿汉模式”
什么是立即加载?立即加载就是使用类的时候已经将对象创建完毕,常见的实现办法就是直接 new 实例化。而立即加载也称为“饿汉模式”。
6.2 延迟加载 / “懒汉模式”
什么是延迟加载?延迟加载就是在调用 get() 方法时实例才被创建,常见的实现办法就是在 get() 方法中进行 new 实例化。延迟加载也称为“懒汉模式”。
1. 延迟加载 / “懒汉模式” 解析
延迟加载 / “懒汉模式” 是在调用方法时实例才被创建。
这种模式如果是在多线程的环境中,就会出现取出多个实例的情况,与单例模式的初衷是相背离的。
2. 延迟加载 / “懒汉模式” 的缺点
“延迟加载”在多线程的环境中,根本不能实现保持单例的状态。
3. 延迟加载 / “懒汉模式”的解决方案
(1)声明 synchronized 关键字
既然多个线程可以同时进入 getInstance() 方法,那么只需要对 getInstance() 方法声明 synchronized 关键字即可。
为 getInstance() 方法加入同步 synchronized 关键字得到相同实例的对象,但此种方法的运行效率非常低下,是同步运行的,下一个线程想要取得对象,则必须等上一个线程释放锁之后,才可以继续执行。
(2)尝试同步代码块
同步方法是对方法的整体进行持锁,这对运行效率来讲是不利的。
同步 synchronized 语句块得到相同实例的对象,但此种方法的运行效率也是非常低的,和 synchronized 同步方法一样是同步运行的。
(3)针对某些重要的代码进行单独的同步
同步代码块可以针对某些重要的代码进行单独的同步,而其他的代码则不需要同步。这样在运行时,效率完全可以得到大幅提升。
此方法使用同步 synchronized 语句块,只对实例化对象的关键代码进行同步,从语句的结构上来讲,运行的效率的确得到了提升。但如果是遇到多线程的情况下还是无法解决得到同一个实例对象的结果。
(4)使用 DCL 双检查锁机制
使用 DCL 双检查锁机制来实现多线程环境中的延迟加载单例设计模式。
DCL 双检查模式就是一方面使用 synchronized 语句款,只对实例化对象的关键代码进行同步,另一方面对单例对象使用 volatile 关键字。
使用双重检查锁功能,成功地解决了“懒汉模式”遇到多线程的问题。DCL 也是大多数多线程结合单例模式使用的解决方案。
6.3 使用静态内置类实现单例模式
DCL 可以解决多线程单例模式的非线程安全问题。当然,使用其他的办法也能达到同样的效果。
public class MyObject {
//内部类方式
public static class MyObjectHandler {
private static MyObject myobject = new MyObject();
}
private MyObject() {
}
public static MyObjectgetInstance() {
return MyObjectHandler.myObject;
}
}
6.4 序列化与反序列化的单例模式实现
静态内置类可以达到线程安全问题,但如果遇到序列化对象时,使用默认的方式运行得到的结果还是多例的(单例类 implements Serializable)。
文件读和写获取的对象实例不同,解决办法就是在反序列中使用 readResolve() 方法。
6.5 使用 static 代码块实现单例模式
静态代码块中的代码在使用类的时候就已经执行了,所以可以应用静态代码块的这个特性来实现单例设计模式。
static {
instance = new MyObject();
}
6.6 使用 enum 枚举数据类型实现单例模式
枚举 enum 和静态代码块的特性相似,在使用枚举类时,构造方法会被自动调用,也可以应用其这个特性实现单例设计模式。
public enum MyObject{
...
private MyObject(){
//单例初始化
}
}
6.7 完善使用 enum 枚举实现单例模式
前面一节将枚举类进行暴露,违反了“职责单一原则”。
public class MyObject{
public enum MyEnumSingletion{
...
private MyEnumSingletion(){
//单例初始化
}
}
}
6.8 本章总结
本章使用若干案例来阐述单例模式与多线程结合时遇到的情况与解决方法。
Java多线程编程核心技术-第6章-单例模式与多线程-读书笔记的更多相关文章
- Java多线程编程核心技术-第4章-Lock的使用-读书笔记
第 4 章 Lock 的使用 本章主要内容 ReentrantLocal 类的使用. ReentrantReadWriteLock 类的使用. 4.1 使用 ReentrantLock 类 在 Jav ...
- Java多线程编程核心技术-第3章-线程间通信-读书笔记
第 3 章 线程间通信 线程是操作系统中独立的个体,但这些个体如果不经过特殊的处理就不能成为一个整体.线程间的通信就是成为整体的必用方案之一,可以说,使线程间进行通信后,系统之间的交互性会更强大,在大 ...
- Java多线程编程核心技术-第1章-Java多线程技能-读书笔记
第 1 章 Java 多线程技能 本章主要内容 线程的启动 如何使线程暂停 如何使线程停止 线程的优先级 线程安全相关的问题 1.1 进程和多线程的概念及线程的优点 进程是操作系统结构的基础:是一次程 ...
- Java编程思想——第17章 容器深入研究 读书笔记(三)
七.队列 排队,先进先出. 除并发应用外Queue只有两个实现:LinkedList,PriorityQueue.他们的差异在于排序而非性能. 一些常用方法: 继承自Collection的方法: ad ...
- Java多线程编程核心技术-第7章-拾遗增补-读书笔记
第 7 章 拾遗增补 本章主要内容 线程组的使用. 如何切换线程状态. SimpleDataFormat 类与多线程的解决办法. 如何处理线程的异常. 7.1 线程的状态 线程对象在不同的运行时期有不 ...
- Java多线程编程核心技术-第5章-定时器 Timer-读书笔记
第 5 章 定时器 Timer 定时 / 计划功能在移动开发领域使用较多,比如 Android 技术.定时计划任务功能在 Java 中主要使用的就是 Timer 对象,他在内部使用多线程的方式进行处理 ...
- Java多线程编程核心技术-第2章-对象及变量的并发访问-读书笔记
第 2 章 对象及变量的并发访问 本章主要内容 synchronized 对象监视器为 Object 时的使用. synchronized 对象监视器为 Class 时的使用. 非线程安全是如何出现的 ...
- java多线程编程核心技术——第三章
第一节等待/通知机制 1.1不使用等待/通知机制实现线程间的通讯 1.2什么是等待/通知机制 1.3等待/通知机制的实现 1.4方法wait()锁释放与notify()锁不释放 1.5当interru ...
- java多线程编程核心技术——第七章补漏拾遗
本章主要知识点: 1)线程组的使用 2)如何切换线程状态 3)SimpleDateFormat类与多线程的解决方法 4)如何处理线程异常. 这本书基本来到了终点,其实在第四章来说,核心(基础)的线程知 ...
随机推荐
- [LeetCode] 43. Multiply Strings 字符串相乘
Given two non-negative integers num1 and num2represented as strings, return the product of num1 and ...
- mac 浏览器(chrome, safari)信任自签名证书
mac 浏览器(chrome, safari)信任自签名证书 自签名证书创建了一个 https 服务器,但是浏览器访问的时候总是不信任证书,感觉很烦,就想如果信任这个证书就不会有问题了. 方法1: 直 ...
- nth-of-type(n)和nth-child(n)的区别
nth-of-type 与nth-child都属于css选择器,都是在同级别节点中找到第n个元素,前者是先确定元素类型,再计算n的位置:后者是先确定n的位置,再确定元素类型 例: <div cl ...
- Linux操作USB手柄
Linux控制原理 Linux C控制JoyStick的比较简单,首先在JoyStick在Linux 安装好驱动后会在/dev/input生成js0.对其设备控制,就是读取相应的结构来判断用户输入哪一 ...
- [转帖]分布式事务之解决方案(XA和2PC)
分布式事务之解决方案(XA和2PC) https://zhuanlan.zhihu.com/p/93459200 3. 分布式事务解决方案之2PC(两阶段提交) 针对不同的分布式场景业界常见的解决方案 ...
- SpringMVC-方法四种类型返回值总结,你用过几种?
SpringMVC 现在算是 Java 领域的一个基础性框架了,很多人天天用,可是对于 SpringMVC 方法的返回值,你又是否完全清楚呢?今天松哥就来和大家聊一聊 SpringMVC 中四种不同类 ...
- Docker安装及简单使用
1.docker安装 #1.检查内核版本,必须是3.10及以上 uname -r #2.安装 yum -y install docker 2.docker简单使用 #1.启动docker system ...
- ELK学习笔记之ElasticSearch的集群(Cluster),节点(Node),分片(Shard),Indices(索引),replicas(备份)之间关系
[Cluster]集群,一个ES集群由一个或多个节点(Node)组成,每个集群都有一个cluster name作为标识----------------------------------------- ...
- PIE SDK影像快速拼接
1.算法功能简介 快速拼接是对若干幅互为邻接的遥感数字图像拼在一起,构成一幅整体影像的技术过程.PIE支持快速拼接算法功能的执行,下面对快速拼接算法功能进行介绍. 2.算法功能实现说明 2.1 实现步 ...
- Linux文本编辑器的常用命令
Vi文本编辑器 首先介绍命令模式,命令模式是在进入文本编辑器的时候的当前状态:输入模式(插入模式)是在插入文本时候按下的键,比如 大小 i 键,a键.o键:底行模式是在命令模式的状态直接输入冒号 & ...