单例(Singleton)模式确保一个类只有一个实例,并提供一个全局访问点。

有一些对象其实我们只需要一个,比方说线程池、缓存、对话框、处理偏好设置和注册表的对象、日志对象、充当外设驱动程序的对象等等。使用单例模式可以确保它们只有一个实例会被创建,且提供了一个全局访问点,在需要时才创建对象,和全局对象一样方便,也不像全局变量一样在程序一开始就创建好对象。

单例模式的实现并不复杂,可以使用私有的构造函数+静态的getterInstance方法来完成。

public class Singleton {private static Singleton uniqueInstance;private Singleton() {}public static Singleton getInstance() {if (uniqueInstance == null) {uniqueInstance = new Singleton();}return uniqueInstance;}
}

下面是单例模式的一个示例,该代码模拟了一个巧克力工厂用锅炉生产巧克力的过程,巧克力锅炉是一个只需要唯一实例的类。

public class ChocolateBoiler {private boolean empty;private boolean boiled;private static ChocolateBoiler uniqueInstance;private ChocolateBoiler() {empty = true;boiled = false;}public static ChocolateBoiler getInstance() {if (uniqueInstance == null) {System.out.println("Creating unique instance of Chocolate Boiler");uniqueInstance = new ChocolateBoiler();}System.out.println("Returning instance of Chocolate Boiler");return uniqueInstance;}public void fill() {if (isEmpty()) {empty = false;boiled = false;// fill the boiler with a milk/chocolate mixture}}public void drain() {if (!isEmpty() && isBoiled()) {// drain the boiled milk and chocolateempty = true;}}public void boil() {if (!isEmpty() && !isBoiled()) {// bring the contents to a boilboiled = true;}}public boolean isEmpty() {return empty;}public boolean isBoiled() {return boiled;}
}
public class ChocolateController {public static void main(String args[]) {ChocolateBoiler boiler = ChocolateBoiler.getInstance();boiler.fill();boiler.boil();boiler.drain();// will return the existing instanceChocolateBoiler boiler2 = ChocolateBoiler.getInstance();}
}

单例模式与多线程

在多线程环境中,使用get方法会出现取出多个实例的情况,与单例模式的初衷违背。 解决方案:

  • 声明synchronized关键字:运行效率低下,下一个线程想要取得对象,必须等上一个线程释放锁后,才可以继续执行。
  • 使用同步代码块:与第一种方法一样同步运行,效率低下
  • 针对某些重要的代码进行单独的同步:只对实例化对象的关键代码进行同步,还是有线程安全问题
  • 使用DCL双检查锁机制:对实例对象加上volatile关键字,在关键代码块上对加了volatile关键字的实例变量的类加上synchronized锁,可以成功解决“懒汉模式”遇到的多线程问题。
  • 使用静态内置类实现单例模式:可以实现和DCL相同的效果。

一个使用DCL的实例如下:

public class DCL {private volatile static DCL uniqueInstance;private DCL() {}public static DCL getInstance() {if (uniqueInstance == null) {synchronized (DCL.class) {if (uniqueInstance == null) {uniqueInstance = new DCL();}}}return uniqueInstance;}
}
public class DCLTest {public static void main(String[] args) {DCL dcl = DCL.getInstance();}
}

设计模式(5)——单例模式相关推荐

  1. socket可以写成单例嘛_精读《设计模式 - Singleton 单例模式》

    Singleton(单例模式) Singleton(单例模式)属于创建型模式,提供一种对象获取方式,保证在一定范围内是唯一的. 意图:保证一个类仅有一个实例,并提供一个访问它的全局访问点. 其实单例模 ...

  2. C#设计模式(1)——单例模式

    原文地址:http://www.cnblogs.com/zhili/p/SingletonPatterm.html 一.引言 最近在设计模式的一些内容,主要的参考书籍是<Head First 设 ...

  3. java设计模式之单例模式(七种方法)

    单例模式:个人认为这个是最简单的一种设计模式,而且也是在我们开发中最常用的一个设计模式. 单例模式的意思就是只有一个实例.单例模式确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例.这个 ...

  4. java单例模式的七种写法_Java设计模式之单例模式的七种写法

    什么是单例模式? 单例模式是一种常见的设计模式,单例模式的写法有很多种,这里主要介绍三种: 懒汉式单例模式.饿汉式单例模式.登记式单例 . 单例模式有以下特点: 1.单例类只能有一个实例. 2.单例类 ...

  5. go设计模式之单例模式

    在这里插入图片描述# go设计模式之单例模式 在软件开发时,经常会遇到有些对象需要保证只有一个实例的,那么这种设计模式就应用而生. 定义 单例模式,也叫单子模式,是一种常用的软件设计模式,属于创建型模 ...

  6. 一篇博客读懂设计模式之---单例模式

    一篇博客读懂设计模式之---单例模式 一.  单例模式 单例对象(Singleton)是一种常用的设计模式.在Java应用中,单例对象能保证在一个JVM中,该对象只有一个实例存在.这样的模式有几个好处 ...

  7. Java 设计模式(3)单例模式

    前言 概念: java中单例模式是一种常见的设计模式,单例模式的写法有好几种,这里主要介绍三种:懒汉式单例.饿汉式单例.登记式单例. 单例模式有以下特点: 1.单例类只能有一个实例. 2.单例类必须自 ...

  8. socket可以写成单例嘛_精读设计模式 Singleton 单例模式

    Singleton(单例模式) Singleton(单例模式)属于创建型模式,提供一种对象获取方式,保证在一定范围内是唯一的. 意图:保证一个类仅有一个实例,并提供一个访问它的全局访问点. 其实单例模 ...

  9. 设计模式之单例模式——Singleton

                        设计模式之单例模式--Singleton 设计意图: 保证类仅有一个实例,并且可以供应用程序全局使用.为了保证这一点,就需要这个类自己创建自己的对象,并且对外有 ...

  10. 实践GoF的设计模式:单例模式

    本文分享自华为云社区<[Go实现]实践GoF的23种设计模式:单例模式>,作者: 元闰子. 简述 GoF 对单例模式(Singleton)的定义如下: Ensure a class onl ...

最新文章

  1. web开发的一些心得
  2. Mac下使用Wine安装Xshell 4和Xftp 4
  3. 20181023-3 每周例行报告
  4. php exec 怎么确定执行成功_php执行系统外部命令的4种方法
  5. 关系型数据库是如何运作的
  6. isight参数优化理论与实例详解_详解oracle数据库优化参数--cursor_sharing
  7. Oracle常用字符串操作
  8. onlyoffice更新中文字体总结
  9. 《剑指Offer》 矩形覆盖
  10. vue中v-model的使用
  11. pandas 索引 —— index、set_index、reset_index
  12. Kotlin(android)协程中文翻译
  13. 手把手BC26模组OpenCPU开发之旅-1.简介
  14. html5页面风格,H5页面设计风格大盘点!
  15. 电源管理允许此设备唤醒计算机怎么关掉,电脑如何设置电源管理允许鼠标唤醒计算机...
  16. java软件工程师培训学_Java软件工程师学习路线
  17. Chrome 截取长图
  18. C++:建立一个被称为sroot()的函数,返回其参数的二次方根。重载sroot()3次,让它返回整数、长整数与双精度的二次方根
  19. assets文件夹资源的访问
  20. defined在c语言中的作用,c语言defined的用法

热门文章

  1. [2019杭电多校第二场][hdu6602]Longest Subarray(线段树)
  2. 保持在Div 底部的方法
  3. 图解clientWidth,offsetWidth,scrollWidth,scrollTop
  4. tomcat的server.xml中的Context节配置
  5. 非常好的Demo网站
  6. 二叉树的非递归遍历(转载)
  7. Guava - Collections - Immutable collections
  8. uni-app之实现分页
  9. com.mysql.jdbc.jdbc2.optional.MysqlXADataSource 找不到
  10. Sql语句对数据库和表的简单操作