单件模式多线程环境下实现

 参考《Head First 设计模式》

单件模式 定义:确保一个类只有一个实例,并提供一个全局的访问点。

单件模式如果没有做同步处理,在多线程环境下很容易造成出现多个实例情况。一下三种实现方式可以解决这个问题。

实现一:

public class Singleton {
	private static Singleton uniqueInstance;
	// other useful instance variables here
	private Singleton() {}
	public static synchronized Singleton getInstance() {
		if (uniqueInstance == null) {
			uniqueInstance = new Singleton();
		}
		return uniqueInstance;
	}
	// other useful methods here
}

 此方法是好理解的一种,但是有个缺陷,在每次调用getInstance()方法都需要进行代码同步,所以代码执行效率会有所降低。还有单例模式在创建实例后就不需要进行同步处理了,如果在调用程序频繁且对性能要求较高的地方尽量少使用此方法。

实现二(急切创建实例):

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

 利用这种做法,JVM在加载这个类是就马上创建此唯一的单件实例。JVM保证在任何线程访问uniqueInstance变量之前,一定先创建此实例。在静态初始化器中创建单件,保证了线程安全

如果程序总是创建并使用单件实例,或者在创建和运行时方面的负担不太繁重,可以考虑此方法。

 实现三(双重检查加锁):

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

 首先检查是否创建实例了,如果未创建才进行同步。这样一来,只有第一次才会进行同步。第一次执行时。进入同步代码块后在检查一次,这样做确保多个线程执行时,创建唯一实例。如果仍是null,才创建实例。

注意此处用到volatile 修饰符,确保变量uniqueInstance被初始化成Singleton实例时,多个线程立即可见

。 

猜你喜欢

转载自tongfeng.iteye.com/blog/2195917