Effective Java学习笔记之一

  今天开始系统看《Effective Java》,将看书的细节记下备忘,并不是总结。

  很早开始就接触到设计模式,特别是最简单的单例模式,Java实现单例模式,我开始的思路是设置一个私有静态类实例化变量,初值设为null,提供一个静态初始化的get方法,if判断变量是否为null选择是否new一个实例。代码如下:

public class ClassicSingleton {
    private static ClassicSingleton instance = null;
    protected ClassicSingleton() {
        
    }
    public static ClassicSingleton getInstance() {
        if(instance == null) {
            instance = new ClassicSingleton();
        }
        return instance;
    }
}

  但是很快看到别人提出这个代码的问题,它不是线程安全的,也就是说在多线程情况下,在if(instance == null)这段代码处切换,导致重复调用会实例化多个不同的实例。开始想不就是个同步吗,只需要加个关键字synchronized在方法getInstance就行了。又涉及到效率问题。

  又提出一种改进声明成公共的final变量,同时由于构造器是似有的确保了唯一性。代码如下:

package singleton.implement;

public class Singleton1 {
    public static final Singleton1 INSTANCE = new Singleton1();
    private Singleton1() {
        
    }
}

但存在反射机制攻击问题

再有就是静态工厂方法,代码如下:

package singleton.implement;

public class Singleton2 {
    private static final Singleton2 INSTANCE = new Singleton2();
    private Singleton2() {
        
    }
    public static Singleton2 getInstance() {
        return INSTANCE;
    }
}

还有就是序列化问题。如果定义的类实现了Serializable接口,在反序列话时会有多个实例生成的问题,需要加readResolve方法

import java.io.Serializable;

public class Singleton2 implements Serializable{
    private static final Singleton2 INSTANCE = new Singleton2();
    private Singleton2() {
        
    }
    public static Singleton2 getInstance() {
        return INSTANCE;
    }
    private Object readResolve() {
        return INSTANCE;
    }
}

最后实现最简单的方法也是最好的是枚举,代码如下:

public enum Singleton3 {
    INSTANCE;
    public void leaveTheBuilding() {
        
    }
}
posted @ 2012-04-23 11:36  菜鸟程序员的奋斗&  阅读(215)  评论(0编辑  收藏  举报