设计模式--创建型模式--单例模式

关键点

构造器私有化
公有的静态方法,返回此类的实例
私有静态的此类的实例

应用场景

当想控制实例的数目,节省系统资源时
类似:数据库连接池(连接池只有一个),线程池

案例代码

/**
 * 单例模式测试:
 * 	单例模式的关键点:
 * 		构造器私有
 * 		因为构造器私有,所以:必须有唯一的入口访问此类的实例 --> 提供一个公有的静态方法,供别的类访问
 * 		因为是在静态方法中,所以:必须 有一个私有的当前类的静态变量应用
 *
 * 	懒汉式、饿汉式的区别:
 * 		关键点在于:对象实例化的时机不同
 *
 * 	为什么饿汉模式,不存在线程安全的问题???
 *          因为:在加载类的时候,对象就实例化了(类加载的时候,是单线程???)
 *
 *
 */
public class SingletonTest {

	public static void main(String[] args) {

		// 饿汉式单例
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(HungerSingleton.getInstance());
				}
			}).start();
		}

		/*// 非线程安全的 懒汉式单例
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(UnSafeSingleton.getInstance());
				}
			}).start();
		}*/

		/*// 线程安全的 懒汉式单例 - 同步方法
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(SafeSingleton.getInstance());
				}
			}).start();
		}*/

		/*// 线程安全的 懒汉式单例 - 同步块
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(SafeSingleton2.getInstance());
				}
			}).start();
		}*/

		/*// 线程安全的 懒汉式单例 - Double Check
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(SafeSingleton3.getInstance());
				}
			}).start();
		}*/

		/*// enum类型的 懒汉式单例
		for(int i=0; i<10; i++) {
			new Thread(new Runnable() {
				@Override
				public void run() {
					System.out.println(EnumSingleton.INSTANCE);
					System.out.println(EnumSingleton.INSTANCE.toUpperCase("yorick"));
				}
			}).start();
		}*/


	}

}























/*===============================饿汉式单例===================================*/
class HungerSingleton {

	private static HungerSingleton instance = new HungerSingleton();

	private HungerSingleton() {}

	public static HungerSingleton getInstance() {
		return instance;
	}

}














/*===============================懒汉式单例===================================*/

/**
 * 懒汉式的单例:非线程安全的
 */
class UnSafeSingleton {

	private static UnSafeSingleton instance = null;

	private UnSafeSingleton() {}

	/**
	 * 单例方法
	 * @return
	 */
	public static UnSafeSingleton getInstance(){
		if (instance == null) {
			instance = new UnSafeSingleton();
		}
		return instance;
	}

}

/**
 * 线程安全的懒汉式单例
 * 缺点:
 * 		性能低:锁的粒度太粗
 */
class SafeSingleton {

	private static SafeSingleton instance = null;

	private SafeSingleton() {}

	public static synchronized SafeSingleton getInstance() {
		if (instance == null) {
			instance = new SafeSingleton();
		}
		return instance;
	}

}


/**
 * 线程安全的懒汉式单例
 * 缺点:
 * 		性能低: 锁的粒度太粗
 */
class SafeSingleton2 {

	private static SafeSingleton2 instance = null;

	private SafeSingleton2() {}

	public static SafeSingleton2 getInstance() {
		synchronized (SafeSingleton2.class){
			if (instance == null) {
				instance = new SafeSingleton2();
			}
		}
		return instance;
	}

}


/**
 * 线程安全的懒汉式单例
 * 缺点:
 * 		性能低: 锁的粒度相对细
 */
class SafeSingleton3 {

	private static SafeSingleton3 instance = null;

	private SafeSingleton3() {}

	public static SafeSingleton3 getInstance() {
		if (instance == null) {
			synchronized (SafeSingleton3.class) {
				if (instance == null) {
					instance = new SafeSingleton3();
				}
			}
		}
		return instance;
	}

}








/*===============================枚举式单例===================================*/
enum EnumSingleton {
	INSTANCE;

	public String toUpperCase(String name) {
		return name.toUpperCase();
	}

}

小小的疑问?

类加载的时候,是单线程进行加载的吗???

posted @ 2021-11-11 10:43  小小落  阅读(30)  评论(0)    收藏  举报