Java设计模式(4)——创建型模式之单例模式(Singleton)
一、概述
弥补一下之前没有给设计模式下的定义,先介绍一下设计模式(引用自百度百科):
设计模式(Design Pattern)是一套被反复使用、多数人知晓的、经过分类的、代码设计经验的总结。使用设计模式的目的:为了代码可重用性、让代码更容易被他人理解、保证代码可靠性。 设计模式使代码编写真正工程化;设计模式是软件工程的基石脉络,如同大厦的结构一样。
设计模式概念的介绍,参见:http://blog.jobbole.com/101076/
其中涉及的设计原则的概念,参见随笔:http://www.cnblogs.com/jiangbei/p/6910790.html
二、单例模式
单例模式:保证整个应用程序中某个类的实例有且只有一个(日志对象等)
常见的单例分为两种——饿汉式和懒汉式
1.饿汉式
通过静态属性:
创建Sinleton类,此类实例只能唯一
public class Singleton {
// 1.构造器私有化,保证不能通过外部创建实例
private Singleton() {
}
// 2.自己内部创建唯一实例
static Singleton instance = new Singleton();
}
因为是静态成员,所以可以通过类.的形式访问:
public class Demo01 {
public static void main(String[] args) {
// 静态方法创建两个对象
Singleton s1 = Singleton.instance;
Singleton s2 = Singleton.instance;
if (s1 == s2) {
System.out.println("s1、s2是同一个实例!");
} else {
System.out.println("s1、s2不是同一个实例!");
}
}
}

通过静态方法:
考虑到我们Java中非常重要的封装的概念,我们有必要对上述代码进行改进,让属性私有化,使得外部无法直接访问:
新的Singleton类:
public class Singleton {
// 1.构造器私有化,保证不能通过外部创建实例
private Singleton() {
}
// 2.创建私有唯一实例
private static Singleton instance = new Singleton();
// 3.对外创建公共的静态方法获取实例
public static Singleton getInstance() {
return instance;
}
}
测试类:
public static void main(String[] args) {
// 静态方法创建两个对象
Singleton s1 = Singleton.getInstance();
Singleton s2 = Singleton.getInstance();
if (s1 == s2) {
System.out.println("s1、s2是同一个实例!");
} else {
System.out.println("s1、s2不是同一个实例!");
}
}

以上就是饿汉式的单例模式,正如其名,饿汉饿汉,饿了就要吃饭,所以它早早的(静态,类加载的时候)就创建好了实例
创建完实例后以后不再改变,所以天生是线程安全的。
2.懒汉式
单例类Singleton2:
public class Singleton2 {
// 1.构造器私有化,不允许外部直接创建
private Singleton2() {
}
// 2.声明静态属性(而不实例化)
private static Singleton2 instance;
// 3.对外提供静态获取方法
public static Singleton2 getInstance() {
if (instance == null) {
instance = new Singleton2();
}
return instance;
}
}
测试类:
public static void main(String[] args) {
// 静态方法创建两个对象
Singleton2 s1 = Singleton2.getInstance();
Singleton2 s2 = Singleton2.getInstance();
if (s1 == s2) {
System.out.println("s1、s2是同一个实例!");
} else {
System.out.println("s1、s2不是同一个实例!");
}
}

懒汉式,也是和它的命名一样,懒得创建对象,初始化时只声明,第一次访问时才创建
当然,不得不指出,上述懒汉式是线程不安全的,多线程下是会存在创建多个实例的问题的,为此我们通过以下的改进方法来保证线程安全:
1.在getInstance()方法上加上同步(返回值前加):
public static synchronized Singleton2 getInstance() {
if (instance == null) {
instance = new Singleton2();
}
return instance;
}
2.双重检查double checking
补充;此种双重检查有待考察,实际中请使用饿汉式!
public static Singleton2 getInstance() {
if (instance == null) {
synchronized (Singleton2.class) {
if (instance == null) {
instance = new Singleton2();
}
}
}
return instance;
}
// 如果没有双重检查,少了任何一重,都会出现要么性能不高,要么创建多个实例
想了解更过有关单例的内容,请参见:http://blog.csdn.net/jason0539/article/details/23297037/
将单例模式中的静态变量(单例)推广到多个静态变量,工厂方法根据参数返回不同的变量,即引申为多例模式!这里不再展开多例模式,可以参阅《Java与模式》一书!
Java设计模式(4)——创建型模式之单例模式(Singleton)的更多相关文章
- Java设计模式_创建型模式_单例模式
单例模式的实现: 定义一个类,在类中定义该类的静态变量,再定一个一个获取该类的静态变量的方法. UML图:
- Java设计模式之创建型模式
创建型模式分为五类:工厂方法模式.抽象工厂模式.单例模式.建造者模式.原型模式 一.工厂方法模式:接口-实现类.工厂类
- Python版设计模式: 创建型模式:单例模式和工厂模式家族
一. 单例模式(Singleton) 所谓单例模式,也就是说不管什么时候都要确保只有一个对象实例存在.很多情况下,整个系统中只需要存在一个对象,所有的信息都从这个对象获取,比如系统的配置对象,或者是线 ...
- java架构之路-(设计模式)五种创建型模式之单例模式
设计模式自身一直不是很了解,但其实我们时刻都在使用这些设计模式的,java有23种设计模式和6大原则. 设计模式是一套被反复使用.多数人知晓的.经过分类编目的.代码设计经验的总结.使用设计模式是为了可 ...
- 设计模式(Java版)-创建型模式之简单工厂模式
前言:这段时间在学习设计模式,本人也是小菜一枚(所以写的如果有错误的地方请大大们给予指出).这个东西也是我一直想学习的,从点点滴滴做起,记录下自己每天的领悟! 一.工厂模式的动机 在软件系统中,经常面 ...
- GoF的23种设计模式之创建型模式的特点和分类
创建型模式的主要关注点是“怎样创建对象?”,它的主要特点是“将对象的创建与使用分离”.这样可以降低系统的耦合度,使用者不需要关注对象的创建细节,对象的创建由相关的工厂来完成.就像我们去商场购买商品时, ...
- Typescript玩转设计模式 之 创建型模式
作者简介 joey 蚂蚁金服·数据体验技术团队 前言 我们团队的工作是用单页面应用的方式实现web工具.涉及到数万到十数万行的前端代码的管理,而且项目周期长达数年. 怎么样很好地管理好这种量级的前端代 ...
- Java 设计模式泛谈&装饰者模式和单例模式
设计模式(Design Pattern) 1.是一套被反复使用.多人知晓的,经过分类编目 的 代码设计经验总结.使用设计模式是为了可重用代码,让代码更容易维护以及扩展. 2.简单的讲:所谓模式就是得到 ...
- 设计模式01 创建型模式 - 单例模式(Singleton Pattern)
参考 [1] 设计模式之:创建型设计模式(6种) | 博客园 [2] 单例模式的八种写法比较 | 博客园 单例模式(Singleton Pattern) 确保一个类有且仅有一个实例,并且为客户提供一 ...
- Java设计模式之职责型模式总结
原创作品,可以转载,但是请标注出处地址:http://www.cnblogs.com/V1haoge/p/6548127.html 所谓职责型模式,就是采用各种模式来分配各个类的职责. 职责型模式包括 ...
随机推荐
- std::unique实现
std::unique适用于将排过序的数据结构重复的部分全部放在结尾 但用的时候发现会将原先容器中的内容改掉,看了源码发现这个函数会将不重复的数据结构直接覆盖到前一个重复的位置上,下面看源码 该函数s ...
- 四、HTTP和HTTPS的区别
1:简介 超文本传输协议HTTP协议被用于在Web浏览器和网站服务器之间传递信息.HTTP协议以明文方式发送内容,不提供任何方式的数据加密,如果攻击者截取了Web浏览器和网站服务器之间的传输报文,就可 ...
- java里面list是引用的好例子
java里面的赋值和引用是不同的,以后要详细总结一下! 看一个例子: public static void main(String[] args) { List<String> list ...
- 输出预测边界框,NMS非极大值抑制
我们预测阶段时: 生成多个锚框 每个锚框预测类别和偏移量 但是,当同一个目标上可能输出较多的相似的预测边界框.我们可以移除相似的预测边界框.——NMS(非极大值抑制). 对于一个预测边界框B,模型会计 ...
- 使用js接收ajax解析的json再拼成一个自己想要的json
//ajax解析的json{ "status": 1, "content": { "pathsInfo": [ { "id&quo ...
- 【SQLSERVER学习笔记】进攻式编程
一般的编程语言建议是进行防御式编程,在开始处理之前先检查所有参数的合法性.但实际上,对数据库编程而言,尽量同时做几件事情的进攻式编程有切实的优势.*/ --我们SP中常见的防御式编程示例:--场景一: ...
- 单独调用kindeditor的多图上传组件实现多图上传
本例是单独调用kindeditor多图上传的组件来进行多图上传,兼容性你懂得! 官方示例地址:http://kindeditor.net/ke4/examples/multi-image-dialog ...
- MySql服务未知原因消失了的解决办法
一: 5.1及后续版本: 打开计算机命令窗口,切换至mysql安装目录,然后运行bin目录下的mysqld.exe,命令如下: D:\MySQL\bin>mysqld.exe -installS ...
- 『ACM C++』 PTA 天梯赛练习集L1 | 036-037
这几天比较忙,所以随便做做水题了,得赶紧把英剧搞完啊啊啊啊啊啊 ------------------------------------------------L1-036-------------- ...
- 『ACM C++』HDU杭电OJ | 1416 - Gizilch (DFS - 深度优先搜索入门)
从周三课开始总算轻松了点,下午能在宿舍研究点题目啥的打一打,还好,刚开学的课程还算跟得上,刚开学的这些课程也是复习以前学过的知识,下半学期也不敢太划水了,被各种人寄予厚望之后瑟瑟发抖,只能努力前行了~ ...