Singleton能确保某一个类只有一个实例。
饿汉式:被加载时即实例化,从资源利用效率来看,较懒汉式稍差;从速度和反应时间看,较懒汉式稍好些。它不能在C++内实现。
EagerSingleton.java
懒汉式:如果加载器是静态的,被加载时不会将自己实例化,直到第一次引用时才实例化(即getInstance()时)。它能在C++内实现。
LazySingleton.java
值得注意的是,懒汉式在多线程的环境下需要考虑解决线程安全的问题。
下面做些修改
public class LazySintleton{ //私有的field,设为null private static final LazySintleton instance=null; /* * 私有构造子,确保外界不能实例化。同时意味着它不能被子类继承。 */ private LazySintleton(){} /* * 静态工厂方法,返回此类的实例 * 在多线程下加个管程(方法声名中使用synchronized关键字) */
public static synchronized LazySintleton getInstance(){
if(instance==null){ instance=new LazySingleton(); }
return this.instance; } /* * 示意商业逻辑 */ public void about(){ System.out.println("This is the LazySingleton pattern."); } }
登记式:GoF为克服懒汉式单例类不能继承的缺点而设计的。注意此处的父类与子类的实现。
RegSingleton.java
RegSingletonChild.java
一个用内部类实现的Singleton,由Jeremy Manson和Brian Goetx于2004年发布。
Singleton.java
在任何使用了EJB、RMI、JINI技术的分散式系统中,应当避免使用有状态的单例。
Edit[2007-4-9]
参考自《java与模式》阎宏。
《java与模式》是本不可多得的好书,值得珍藏!
饿汉式:被加载时即实例化,从资源利用效率来看,较懒汉式稍差;从速度和反应时间看,较懒汉式稍好些。它不能在C++内实现。
EagerSingleton.java
java 代码
public class EagerSingleton{ //私有field,并实自身例化 private static final EagerSingleton instance=new EagerSingleton(); /* * 私有构造子,确保外界不能实例化。同时意味着它不能被子类继承。 */ private EagerSingleton(){} /* * 静态工厂方法,返回此类的实例 */ public static EagerSingleton getInstance(){ return this.instance; } /* * 示意商业逻辑 */ public void about(){ System.out.println("This is the EagerSingleton pattern."); } }
懒汉式:如果加载器是静态的,被加载时不会将自己实例化,直到第一次引用时才实例化(即getInstance()时)。它能在C++内实现。
LazySingleton.java
java 代码
public class LazySintleton{ //私有的field,设为null private static final LazySintleton instance=null; /* * 私有构造子,确保外界不能实例化。同时意味着它不能被子类继承。 */ private LazySintleton(){} /* * 静态工厂方法,返回此类的实例 */ public static LazySintleton getInstance(){ if(instance==null){ instance=new LazySingleton(); }
return this.instance; } /* * 示意商业逻辑 */ public void about(){ System.out.println("This is the LazySingleton pattern."); } }
return this.instance; } /* * 示意商业逻辑 */ public void about(){ System.out.println("This is the LazySingleton pattern."); } }
值得注意的是,懒汉式在多线程的环境下需要考虑解决线程安全的问题。
下面做些修改
public class LazySintleton{ //私有的field,设为null private static final LazySintleton instance=null; /* * 私有构造子,确保外界不能实例化。同时意味着它不能被子类继承。 */ private LazySintleton(){} /* * 静态工厂方法,返回此类的实例 * 在多线程下加个管程(方法声名中使用synchronized关键字) */
public static synchronized LazySintleton getInstance(){
if(instance==null){ instance=new LazySingleton(); }
return this.instance; } /* * 示意商业逻辑 */ public void about(){ System.out.println("This is the LazySingleton pattern."); } }
登记式:GoF为克服懒汉式单例类不能继承的缺点而设计的。注意此处的父类与子类的实现。
RegSingleton.java
java 代码
import java.util.HashMap; public class RegSingleton{ static private HashMap registry=new HashMap(); static { RegSingleton x=new RegSingleton(); registry.put(x.getClass().getName(),x); } /* *保护的构造子 */ protected Regsingleton(){} /** *静态工厂方法,返还此类唯一的实例 */ public static RegSingleton getInstance(String name){ if(name==null){ name="RegSingleton"; } if(registry.get(name)==null){ try{ registry.put(Class.forName(name).newInstance()); } catch(Exception e){ System.out.println ("Error:" +e.toString()); } } return (RegSingleton)(registry.get(name)); } /** *示意性商业逻辑 */ public void about(){ System.out.println ("This is a base Class of RegSingleton "); } }
子类的实现
RegSingletonChild.java
java 代码
import java.util.HashMap; public class RegSingletonChild extends RegSingleton{ public RegSingleChild(){} /** *静态工厂方法 */ public static RegSingletonChild getInstance(){ return(RegSingleChild)RegSingleton.getInstance("RegSingletonChild"); } /** *示意性商业逻辑 */ public void about(){ System.out.println ("This is the child Class extends from RegSingleton class.") } }
一个用内部类实现的Singleton,由Jeremy Manson和Brian Goetx于2004年发布。
Singleton.java
java 代码
public class Singleton{ /** *通过内部类实例化 */ static class SingletonHolder{ static Singleton instance=new Singleton(); } private Singleton(){} public static Singleton getInstance(){ return SingletonHolder.instance; } public void about(){ System.out.println ("test..."); } }
在任何使用了EJB、RMI、JINI技术的分散式系统中,应当避免使用有状态的单例。
Edit[2007-4-9]
参考自《java与模式》阎宏。
《java与模式》是本不可多得的好书,值得珍藏!