单例模式
顾名思义,就是只有单一对象实例。即,程序运行时该类只存在一个实例对象。可充当全局变量使用,保证数据的唯一性。
单例模式属于创建型模式,比较简单的设计模式,轻松学会,轻松使用。
原因
对于很多类来说,单例是十分重要的,主要存在于系统资源浪费等问题。比如我们熟知的windows系统下的任务管理器,不管你Ctrl+Shift+Esc多少次,它都只显示一个任务管理器,因为它不要两个或多个,这样既浪费资源还要保证数据的及时同步更新。还有我们的系统时钟,音频管理etc。上述类型就不需要多个实例,所以前辈们很明智的发现了单例这一美好设计。
使用
1. 将对象保存在成员属性,静态方法getInstance() 获得类对象。(由于构造方法是private私有的,所有其他类不能通过new 来创建对象,保证了唯一)。
class SingleInstance {
SingleInstance static instance = new SingleInstance();
private SingleInstance() {
// code
}
public static getInstance() {
return instance;
}
}
2. 程序运行 静态 getInstance() 获得对象,第一次运行时创建对象。
class SingleInstance {
SingleInstance static instance;
private SingleInstance() {
// code
}
public static SingleInstance getInstance() {
if (instance == null) {
instance = new SingleInstance();
}
return instance;
}
}
3. 为了防止多个线程同时运行静态方法getInstance 获得对象实例,instance 还没来的及new和赋值 就被其他线程以为是null,多次new出实例,所以我们在第1,2方法里加入了同步锁。
public static synchronized SingleInstance getInstance()
4. 遗憾的是,整个方法加入同步锁,让效率低下了。所以机制的前辈提出里终极方案 —— 双重同步检测锁定,将同步语句放入 if 语句。
public static SingleInstance getInstance() {
if (instance == null)
synchronized (SingleInstance.class) {
if (instance == null)
instance = new SingleInstance();
}
return instance;
}
调用
使用时,类名+ . +getInstance() 即可获得实例。
单例和静态类的差别
- 单例可以继承 ,静态类不可以
- 单例可以控制初始化 ,静态类不可以
- 单例一般要联系类里已有数据 静态类一般组织域逻辑,比如说:Math.floor(num)。