第二章 创建和销毁对象
第一条:考虑用静态工厂方法代替构造函数
好处:
1. 与构造函数不同,静态工厂方法具有名字
使用静态工厂方法创建对象可以让用户更容易读懂,表述的更清楚。 因为静态工厂方法有自己的名字,所以它们没有构造函数那样的限制,对于给定的原型特征,可以有不止一个静态的工厂方法。如果一个类看起来需要多个构造函数,并且它们的原型特征相同,那么应该考虑用静态方法来代替其中一个或多个构造函数,并且慎重的选择它们的名字以便明显地标示出它们的不同。
2. 与构造函数不同,它们每次被调用的时候,不要求非得创建一个新的对象。
这样可以避免创建重复的对象,静态工厂方法可以返回同一个对象。
静态工厂方法可以为重复的调用返回同一对象,这也可以被用来控制“在某一时刻那些实例应该优先存在”。这样做有两个理由,第一,它使得一个类可以保证是一个singleton(单例模式)。第二,它使非可变类可以保证“不会有两个相等的实例存在”,即当且仅当a == b的时候才有a.equals(b)为true。如果一个类保证了这一点,那么它的客户可以用==操作代替equals()方法,其结果是实质性的性能提高。
3. 与构造函数不同,它们可以返回一个原返回类型的子类型对象。这样我们在选择被返回对象的类型是就有了更大的灵活性。
这种灵活性的一个应用是,一个API可以返回一个对象,同时又不使该对象的类成为公有的。以这种方式把具体的实现隐藏起来。
缺点:
1. 类如果不含公有的或者受保护的构造函数,就不能被子类化。
2. 它们与其它的静态方法没有任何区别
静态工厂方法的一般命名
valueOf()、getInstance()
第二条 使用私有的构造函数强化singleton属性
有两种方法可以实现,第一种使用私有的构造函数,公有静态成员是一个final域
public class Test{
public static final Test INSTANCE = new Test();
private Test(){
}
}
第二种方法提供了一个公有的静态工厂方法,而不是公有静态final域
public class Test{
private static final Test INSTANCE = new Test();
pirvate Test(){
}
public Test getInstance(){
return INSTANCE;
}
}
第一种方法在性能上稍微领先,而第二种方法提供了灵活性。在不改变API的前提下,允许我们改变思想,可以把类作为singleton或者不做为singleton。
为了使一个singleton类变成可序列化的,仅仅在声明中加上"implements Serializale"是不够的,必须也提供一个readResolve方法。否则的话,一个序列化的实例在每次反序列化的时候,都会产生一个新的实例。
第三条 通过私有构造函数强化不可实例化的能力
这种用法的副作用,使得一个类不可能被子类化
第四条 避免创建重复的对象
第五条 消除过期对象的引用
只要一个类自己管理它的内存,程序员就应该警惕内存泄露问题。内存泄露的另一种常见来源是缓存。
第六条 避免使用终结函数
终结函数不一定会被调用,也不一定会马上被调用。