关于Singleton的意图、动机之类去看书吧,这里只是讨论用java实现时需要注意的一些问题。
   
在java的标准库中就有Singleton的实现--java.lang.Math,所有的方法都是静态方法,所有成员变量定义为static就一切
ok了。这样实际上根本不需要产生任何对象,所有的操作都是用类来实现的,确切的说是Zeroton,不过效果都一样,实现可能更简洁。log4j
中的LogManager也是用这种方法。这种方式实现的Singleton是Stateless的,可以看做是一个工具方法集.
    还有一种不常见的实现如下:
 1class PrintSpooler
 2{
 3//this is a prototype for a printer-spooler class
 4//such that only one instance can ever exist
 5staticboolean
 6instance_flag=false; //true if 1 instance
 7public PrintSpooler() throws SingletonException
 8{
 9if (instance_flag)
10thrownew SingletonException("Only one spooler allowed");
11else
12instance_flag =true; //set flag for 1 instance
13System.out.println("spooler opened");
14}
15//-------------------------------------------
16publicvoid finalize()
17{
18instance_flag =false; //clear if destroyed
19}
20}
	这种方法并不适合java(也许适合C++),因为垃圾回收的时机是无法控制的,对于一个不
再使用的对象由于没有被回收无法创建新的对象。
	用的最多的方法是所谓的 static method.这种方式是Stateful的.在多线程的环境下要注意
同步问题.
 1import java.io.FileInputStream;
 2import java.io.IOException;
 3import java.io.ObjectInputStream;
 4import java.io.ObjectStreamException;
 5import java.io.Serializable;
 6
 7/**
 8 * 
 9*/
10
11/**
12 * @author bahamut
13 * @version 2005-9-22
14*/
15publicfinalclass MySingleton implements Serializable {
16
17privatestatic MySingleton instance =null;
18
19private String             name;
20
21publicstaticsynchronized MySingleton getInstance() {
22if (instance ==null) {
23            instance =new MySingleton();
24        }
25return instance;
26    }
27
28// public Object clone() throws CloneNotSupportedException {
29// throw new CloneNotSupportedException();
30// }
31
32public String getName() {
33return name;
34    }
35
36private MySingleton() {
37        name =this.getClass().getName();
38    }
39
40    Object readResolve() throws ObjectStreamException {
41return getInstance();
42    }
43
44publicstaticvoid main(String arg[]) throws IOException,
45            ClassNotFoundException {
46
47//        MySingleton singleton = MySingleton.getInstance();
48//        ObjectOutputStream out = new ObjectOutputStream(new
49//                FileOutputStream("out"));
50//        out.writeObject(singleton);
51//        out.close();
52
53        MySingleton deserializable =null;
54        ObjectInputStream in =new ObjectInputStream(new FileInputStream("out"));
55        deserializable = (MySingleton) in.readObject();
56        in.close();
57        System.out.println(deserializable.getName());
58        MySingleton singleton = MySingleton.getInstance();
59if (deserializable == singleton) {
60            System.out.println("They are same object");
61        } else {
62            System.out.println("They are not same object");
63        }
64    }
65}
66
	有几点需要注意:
	1。构造函数必须是private,这样才能防止通过new运算符创建对象,这样的类也必然是final的
	2。getInstance() 方法必须是同步的,关于这里同步的问题 
	http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html有详细的论述
	3。最好实现 clone() 方法,防止通过clone()产生多个对象
	4。对于实现Serializable接口的Singleton要实现 Object readResolve(),(详见jdk文档的
	Serializable部分),可以防止由序列化而产生的多个对象。
	5。其他可能产生多个对象的情况参见
	http://java.sun.com/developer/technicalArticles/Programming/singletons/
 
	posted on 2005-10-04 12:30 
JBahamut 阅读(136) 
评论(0)  编辑  收藏