effective java 第三章 (笔记)

第3章 对于所有对象都通用的方法

Object类 主要是为了扩展。所有非final方法都有通用的约定(它们被设计成是要被override)

*** 第8条:覆盖equals时请遵守通用约定 ***

equals方法实现了等价关系:
自反性,对称性,传递性,一致性,非null的引用值x,x.equals(null)必须是false

里氏替换原则:一个类型的任何重要属性将适用于他的子类型,因此为该类型编写的任何方法,在它的子类型上也应同样运行得很好。

权宜之计:复合代替基础

public class ColorPoint{
    private final Point point ;
    private final Color color ;
    
    public ColorPoint(int x , int y ,Color color){
        if(color == null)
            throw new NullPointerException();
        point = new Point(x,y);
        this.color = color ;
    }

    public Point asPoint(){
        return point ;
    }

    @Override
    public boolean equals(Object o ){
        if(!(o instanceof ColorPoint))
            return false;
        ColorPoint cp = (ColorPoint) o ;
        return cp.point.equals(point) && cp.color.equals(color);
    }
… …

}

考虑可变与不可变:相等的对象永远相等,不相等的对象永远不相等。

不要使equals方法依赖于不可靠的资源。

实现高质量equals方法的诀窍:

1.使用== 检查“参数是否为这个对象的引用”
2.instanceof 检查是否是正确类型
3.把参数转换成正确的类型
4.对于关键域,检查参数的域与该对象中对应的域是否相匹配
Float.compare() Double.compare() Arrays.equals()

5.覆盖equals时总要覆盖hashCode;不要企图让equals过于只能;不要将equals声明中的Object对象替换为其他的类型。

*** 第9条:覆盖equals时总要覆盖hashCode ***

相等的对象必须有相等的hash code.

一个好的散列函数通常倾向于“为不相等的对象产生不相等的散列码”

不要试图从散列码计算中排除掉一个对象的关键部分来提高性能。

*** 第10条:始终要覆盖toString ***

Object提供了toString()的一个实现:类名称@散列码的无符号十六进制

实际应用中,toString()应返回对象中包含所有值得关注的信息。

无论你是否决定指定格式,都应该在文档中说明。

*** 第11条:谨慎地覆盖clone ***

对于Cloneable接口,它改变了超类中受保护的方法的行为。

无需调用构造器就可以创建对象。

如果你覆盖了非final类中的clone方法,则应该返回一个通过调用super.clone而得到的对象

从1.5引入了协变返回类型作为泛型。

确保它不会伤害到原始的对象,并确保正确地创建克隆对象中的约束条件。

另一个实现对象拷贝的好办法是提供一个拷贝构造器活拷贝工厂。

最好不用。

*** 第12条:考虑实现Comparable接口 ***

compareTo是Comparable接口种唯一的方法

java平台类库中所有值类都实现了Comparable接口 。

sgn(表达式) :-1 0 1

顺序:从最关键域逐步进行到所有重要的域,

你可能感兴趣的:(effective java 第三章 (笔记))