设计模式: 对问题行之有效的解决方式, 其实它是一种思想.

单例设计模式

解决的问题:就是可以保证一个类在内存中的对象唯一性. 即单个实例.

比如对于A 和 B 两个程序使用同一个配置信息对象时, A 对配置信息作出修改, B 也与之对应的更新配置信息, 即需要保证该对象的唯一性.

如何保证对象唯一性呢?

不允许其他程序用 new 创建该类对象

在该类中创建一个本类实例

对外提供一个方法让其他程序可以获取该对象.

步骤:

私有化该类构造函数

通过 new 在本类中创建一个本类对象

定义一个公有方法, 将创建的对象返回

两种方式

饿汉式: 类一加载, 对象就存在了.

懒汉式: 类加载进来, 没有对象, 只有调用 getInstance 方法时, 才会创建对象.

也称为 单例设计模式的延迟加载模式. 但是, 懒汉式在多线程访问时,存在安全隐患.

// 第一种方式: 饿汉式

class Single

{

Single s = new Single(); // 在本类中创建一个本类对象

private Single(){} // 私有化该类构造函数

// 定义一个公有方法, 将创建的对象返回. 用于返回对象 s, 所以返回类型 Single

public Single getInstance()

{

return s;

}

}

class SingleDemo

{

public static void main(String[] args)

{

Single ss = Single.getInstance();

}

}

/*

分析一: main 函数中, getInstance 方法调用不能使用对象调用, 只能使用类名调用.

所以 Single 类中该方法需要使用 static 修饰.

分析二: getInstance 方法为静态方法, 它访问的内容必须是静态的,所以对象 s 也需要静态修饰.

*/

// 改进

class Single

{

private static Single s = new Single();

private Single(){}

public static Single getInstance() // 提供该方法访问实例对象 s, 是为了对象的可控

{

return s;

}

}

class SingleDemo

{

public static void main(String[] args)

{

Single ss = Single.getInstance();

}

}

// 第二种方式: 懒汉式

// 类加载进来, 没有对象, 只有调用 getInstance 方法时, 才会创建对象.

class Single2

{

private static Single2 s = null;

private Single(){}

public static Single2 getInstance()

{

if(s==null)

s = new Single2();

return s;

}

}

// 示例:下列代码的输出结果

class SingleDemo

{

public static void main(String[] args)

{

Test t1 = Test.getInstance();

Test t2 = Test.getInstance();

t1.setNum(10);

t2.setNum(20);

System.out.println(t1.getNum()); // 输出 20

System.out.println(t2.getNum()); // 输出 20

}

}

class Test

{

private int num;

private static Test t = new Test();

private Test(){}

public static Test getInstance()

{

return t;

}

public void setNum(int num)

{

this.num = num;

}

public int getNum()

{

return num;

}

}

// 懒汉式二:避免多线程同时调用getInstance()方法, 可以使用关键字synchronized

class LazySingleton {

private static LazySingleton instance = null;

private LazySingleton(){}

public synchronized static LazySingleton getInstance() {

if(instance == null){

instance = new LazySingleton();

}

return instance;

}

}

// 懒汉式三:为提高系统性能,对"instance = new LazySingleton()"进行锁定

class LazySingleton{

private static LazySingleton instance = null;

private LazySingleton(){}

public static LazySingleton getInstance(){

if(instance == null){ // 此处,有可能造成单例对象不唯一

synchronized(LazySingleton.class){

instance = new LazySingleton();

}

}

return instance;

}

}

// 懒汉式四:双重检查锁定(Double-Check Locking)

class LazySingleton{

// 注意,此处增加修饰符 volatile

private volatile static LazySingleton instance = null;

private LazySingleton(){}

public static LazySingleton getInstance(){

// 第一重判断

if(instance == null){

// 锁定代码块

synchronized(LazySingleton.class){

// 第二重判断

if(instance == null){

instance = new LazySingleton();

}

}

}

return instance;

}

}

//单例第三种方式: Initialization Demand Holder(IoDH)技术

// 在单例类中增加一个静态(static)内部类

class Singleton{

private Singleton(){}

// 静态类

private static class HolderClass {

private final static Singleton instance = new Singleton();

}

public static Singleton getInstance() {

return HolderClass.instance;

}

public static void main(String args[]){

Singleton s1, s2;

s1 = Singleton.getInstance();

s2 = Singleton.getInstance();

System.out.println(s1 == s2);

}

}

_参考资料_

- [JavaSE 基础视频(毕向东)](https://www.bilibili.com/video/av3092292/#page=4)

- [单例模式中的双重检查](http://blog.csdn.net/chenchaofuck1/article/details/51702129)

java 单例设计_Java 之单例设计模式相关推荐

  1. java 抽象属性 设计_Java 抽象类与模板设计模式详解

    抽象类 抽象类是为了方法覆写而提供的类结构,因为其无法自身直接进行对象实例化操作,所以在实际应用中,抽象类主要目的是进行过程操作使用,当你要使用抽象类进行开发的时候,往往都是在你设计中需要解决类继承问 ...

  2. 6大设计原则与java 23种设计模型之单例,工厂,装饰,观察者,责任链,代理,适配器,策略

    设计原则 设计模式的6大原则,单一职责原则,开放封闭原则,里式替换原则,依赖导致原则,迪米特原则和接口隔离原则. 单一职责原则: 一个类只负责一个功能领域中的相应职责.高内聚,低耦合. 开闭原则: 对 ...

  3. 【用例设计】接口用例设计

    在接口测试过程中,用例设计是关键中的关键,需要重点关注的一些维度 接口测试 什么是接口 接口就是内部模块对模块,外部系统对其他服务提供的一种可调用或者连接的能力的标准,所谓的接口是模块与模块之间的一种 ...

  4. java五子棋课程设计_JAVA课程设计+五子棋游戏

    1. 团队课程设计博客链接 2. 个人负责模块或任务说明 1.在同伴构建好初始框图的情况下,编写一个继承JPanel类,实现添加控件. 2.编写paintComponent类,实现绘画棋盘还有棋子. ...

  5. java 单例 实现_java 实现单例的各种方式

    概述 上一篇日志中,我们介绍了单例模式的概念和基础的应用 本节中,我们就来介绍一下 java 语言中如何编写单例模式类 只适合单线程环境的单例模式 public class Singleton { p ...

  6. java 单链表反转_Java实现单链表翻转详解

    单链表翻转比如有如下链表: 需要按照C B A 输出,我们可以有好几种方法: package org.andy.test; import java.util.ArrayList; import jav ...

  7. java订单重复提交_java表单重复提交常用解决办法

    最近在看些基础的东西,顺便做下笔记.相信大家在平时网页使用中,经常会有按钮重复点击,然后点不动刷新,还有当网络延时比较厉害点了没反应在点击的重复提交.为了避免这种情况,总结了一下4点处理方案 表单重复 ...

  8. java 反转jia链表_Java实现单链表反转

    本文主要介绍单链表反转的两种方法,记录如下: 1. package com.leetcode; public class ListReverse { public static void main(S ...

  9. java工作流 表设计_Java工作流系统jflow从表功能介绍一

    关键词:工作流快速开发平台  工作流流设计  业务流程管理   asp.net 开源工作流  bpm工作流系统  java工作流主流框架  自定义工作流引擎 表单设计器  流程设计器 从表也叫明细表, ...

最新文章

  1. arraylist 后往前遍历_面试官:谈谈常用的Arraylist和Linkedlist的区别
  2. java使用正则表达为数字添加千位符的简单方法
  3. 微信小程序尝鲜一个月现状分析
  4. [转]URL汉字编码问题(及乱码解决)
  5. 音乐应用开发Android应用开发--MP3音乐播放器界面设计(2)
  6. pytorch笔记——简易回归问题
  7. 20165223《Java程序设计》第八周Java学习总结
  8. java集合——集合接口+迭代器接口
  9. 成为Java流大师–第1部分:创建流
  10. Qt 【关于控件样式,鼠标进入、离开、点击】
  11. Git Pull Failed:Could not read from remote repository
  12. iframe自适应高度调整
  13. IE6 的 hover 伪类 bug
  14. 深度学习笔记_基本概念_逆卷积的详细解释ConvTranspose2d(fractionally-strided convolutions)
  15. MATLAB中simulink的模糊PID控制
  16. iis 程序池设置及详解
  17. c语言rst关系,为什么服务器突然回复RST——小心网络中的安全设备
  18. Markdown 编辑器设置字体大小颜色
  19. 4.22 虾皮_小米_度小满
  20. 如何用计算机远程桌面连接不上,手把手教你电脑远程桌面无法连接怎么办

热门文章

  1. 创建非矩形的Windows 窗体
  2. JSON.parse和JSON.stringify方法
  3. C#动态加载dll,dll目录指定
  4. 2018.10.18多校
  5. Gym 100090D Insomnia
  6. 第一百四十五节,JavaScript,同步动画
  7. YTU 2924: 文件操作--二进制文件读入
  8. linux rar安装
  9. js 数组(Array)
  10. 【转】使用JDK自带jvisualvm监控tomcat