在GoF的23种设计模式中,Singleton模式(中文称为单态或单件模式)是比较常用的模式之一.它的目的是保在调用期间, 一个类只有一个实例存在.最典型的例子为数据库连接, 数据库连接只需要一个, 所以可以使用单态模式.使用单态模式时, 创建数据库连接的方法, 只能为静态, 并且要保证方法的同步, 否则在多线程操作中, 有可能会创建多个实例.
Singleton模式有两种写法,我们先用C#语言来写写第一种:
public sealed class Singleton
{
private Singleton()
{}
public static readonly Singleton Instance = new Singleton();
public void MethodA()
{ ... }
}
己声明自己的实例,是不是有些奇怪?这里是单态模式写法的重点,调用这个类的方法MethodA的时候,应该使用Singleton.Instance.MethodA();注意这里的Instance还需要加上static和readonly修饰符.
单态模式还需要注意的地方是:私有的构造函数,这是为了防止在类的外部被实例化,类的sealed修饰符,这是为了防止类被继承后变相产生多个实例.
下面我们通过写一个数据库连接,来看一下Singleton模式的第二种写法(Lazy Initialization):
[Synchronization()]
public sealed class ConnectionClass
{
private static OleDbConnection instance = null;
private static string connectionString =
@"Provider=Microsoft.Jet.OLEDB.4.0;User ID=Admin;Data Source=D:\My Documents\测试文件\book.mdb";
public static OleDbConnection GetInstance()
{
if (instance == null)
{
Console.WriteLine("创建一个新的连接.");
instance = new OleDbConnection(connectionString);
}
return instance;
}
}
public class SingletonSample
{
public static void Main()
{
OleDbConnection connection = ConnectionClass.GetInstance();
connection.Open();
// 进行一些操作
......
connection = ConnectionClass.GetInstance();
connection.Close();
}
}
注意到Lazy Initialization形式中的Synchronization,这个Synchronization很重要,如果没有Synchronization,那么使用getInstance()是有可能得到多个Singleton实例。
我们还可以根据上面的代码对Singleton模式进行扩展,使它不仅适用于限定一个实例,也能支持两个实例,乃至指定数目的多个实例.限于篇幅,我就不多做介绍了.
从这里可以看出,设计模式是程序员真正掌握面向对象核心思想的必修课,它并不是一种具体"技术",它讲述的是思想,它展示了接口或抽象类在实际案例中的灵活应用和智慧.