单例模式
恶汉式:
以下实现中,私有静态变量 unInstance 被延迟实例化,这样做的好处是,如果没有用到该类,那么就不会实例化 uniqueInstance,从而节约资源。
这个实现在多线程环境下是不安全的,如果多个线程能够同时进入 if (unInstance == null)
,并且此时 unInstance 为 null,那么会有多个线程执行 unInstance = new Singleton();
语句,这将导致实例化多次 unInstance。
/** * */ package com.cxy; /** * @author Administrator * */ public class Singleton { public static Singleton unSingleton; public Singleton() { } public Singleton getInstance() { if(unSingleton == null) { return new Singleton(); } return unSingleton; } }
恶汉式 安全的:
线程不安全问题主要是由于 getInstance 被实例化多次,采取直接实例化 getInstance 的方式就不会产生线程不安全问题。
但是直接实例化的方式也丢失了延迟实例化带来的节约资源的好处。
/** * */ package com.cxy; /** * @author Administrator * */ public class Singleton { public static Singleton unSingleton =new Singleton(); public Singleton() { } public Singleton getInstance() { if(unSingleton == null) { return new Singleton(); } return unSingleton; } }
懒汉式:
只需要对 getInstance() 方法加锁,那么在一个时间点只能有一个线程能够进入该方法,从而避免了实例化多次 unInstance。
但是当一个线程进入该方法之后,其它试图进入该方法的线程都必须等待,即使 unInstance 已经被实例化了。这会让线程阻塞时间过长,因此该方法有性能问题,不推荐使用
/** * */ package com.cxy; /** * @author Administrator * */ public class Singleton { public static Singleton unSingleton =new Singleton(); public Singleton() { } public static synchronized Singleton getInstance() { if(unSingleton == null) { return new Singleton(); } return unSingleton; } }
/** * */ package com.cxy; /** * @author Administrator * */ public class Singleton { public static Singleton unSingleton =new Singleton(); public Singleton() { } public static Singleton getInstance() { if(unSingleton == null) { synchronized(Singleton.class) { if(unSingleton == null) { return new Singleton(); } } } return unSingleton; } }
上面是doublecheck模式
静态内部模式:
/** * */ package com.cxy; /** * @author Administrator * */ public class Singleton { private static class SingletonInner{ public static Singleton instance; static { instance =new Singleton(); } public static Singleton getInstance() { return instance; } } public static Singleton getInstace() { return SingletonInner.getInstance(); } }
这个是静态内部类的方式来初始化