No8 覆盖equals方法时请遵守通用约定

通用约定,下面的约定前提都是x/y/z不为null值。

  1. 自反性(reflexive),x.equals(x)必须返回true。
  2. 对称性(symmetric),当且仅当y.equals(x)返回true时,x.equals(y)必须返回true。
  3. 传递性(transitive),如果x.equals(y)返回true,并且y.equals(z)也返回true,那么x.equals(z)也必须返回true。
  4. 一致性(consistent),信息没有修改的情况下,多次调用x.equals(y)的返回结果必须一致。
  5. x.equals(null)必须返回false。

诀窍:

  1. 使用“==”操作符检查“参数是否为对这个对象的引用”。
  2. 使用“instanceof”操作符检查“参数是否为正确的类型”。
  3. 把参数转换为正确的类型。
  4. 对于该类中的每个“关键(significant)”域,检查参数中的域是否与该对象中对应的域相匹配。

No9 覆盖equals方法时总要覆盖hashCode

为不相等的对象产生不相等的散列码”,这正是hashCode约定中第三条的含义。计算hashCode示范代码:

@Override 
public int hashCode() {
int result = 17;
result = 31 * result + areaCode;
result = 31 * result + prefix;
result = 31 * result + lineNumber; return result;
}

31有个很好的特性,即用移位和减法来代替乘法,可以得到更好的性能:31*i == (i<<5)-i。现代的VM可以自动完成这种优化。

如果计算散列码的开销比较大,可以考虑缓存,只计算一次等方法。

No10 始终覆盖toString

建议所有的子类都覆盖这个方法”。在实际应用中,toString方法应该返回对象中包含的所有值得关注的信息。

无论你是否决定指定格式,都应该在文档中明确地表明你的意图。示范:

/**
* Returns the string representation of this phone number.
* The string consists of fourteen characters whose format
* is "(XXX) YYY-ZZZZ", where XXX is the area code, YYY is
* the prefix, and ZZZZ is the line number. (Each of the
* capital letters represents a single decimal digit.)
*
* If any of the three parts of this phone number is too small
* to fill up its field, the field is padded with leading zeros.
* For example, if the value of the line number is 123, the last
* four characters of the string representation will be "0123".
*
* Note that there is a single space separating the closing
* parenthesis after the area code from the first digit of the
* prefix.
*/ @Override
public String toString() {
return String.format("(%03d) %03d-%04d",
areaCode, prefix, lineNumber);
}

No12 考虑实现Comparable接口

compareTo方法的通用约定与equals方法的相似:将这个对象与指定的对象进行比较。当该对象小于、等于或大于指定对象的时候,分别返回一个负整数、零或者正整数。如果由于指定对象的类型而无法与该对象进行比较,则抛出ClassCastException异常。

强烈建议(x.compareTo(y) == 0) == (x.equals(y)),但这并非绝对必要。

如果一个类有多个关键域,你必须从最关键的域开始,逐步进行到所有的重要域。

示范代码:

    public int compareTo(PhoneNumber pn) {
// Compare area codes
int areaCodeDiff = areaCode - pn.areaCode;
if (areaCodeDiff != 0)
return areaCodeDiff; // Area codes are equal, compare prefixes
int prefixDiff = prefix - pn.prefix;
if (prefixDiff != 0)
return prefixDiff; // Area codes and prefixes are equal, compare line numbers
return lineNumber - pn.lineNumber;
}

《Effective Java》读书笔记二(通用方法)的更多相关文章

  1. Effective Java 读书笔记之七 通用程序设计

    一.将局部变量的作用域最小化 1.在第一次使用变量的地方声明 2.几乎每个变量的声明都应该包含一个初始化表达式:try-catch语句是一个例外 3.使方法小而集中是一个好的策略 二.for-each ...

  2. Effective Java 读书笔记(一):使用静态工厂方法代替构造器

    这是Effective Java第2章提出的第一条建议: 考虑用静态工厂方法代替构造器 此处的静态工厂方法并不是设计模式,主要指static修饰的静态方法,关于static的说明可以参考之前的博文&l ...

  3. Effective java读书笔记

    2015年进步很小,看的书也不是很多,感觉自己都要废了,2016是沉淀的一年,在这一年中要不断学习.看书,努力提升自己 计在16年要看12本书,主要涉及java基础.Spring研究.java并发.J ...

  4. java读书笔记二

    这是我的一些读书笔记: 我研究了一下面向对象: 面向对象符合人类看待事物的一般规律,对象的方法的实现细节是包装的,只有对象方法的实现者了解细节 我觉得面向过程是由过程.步骤.函数组成,过程是核心,面向 ...

  5. Effective Java读书笔记完结啦

    Effective Java是一本经典的书, 很实用的Java进阶读物, 提供了各个方面的best practices. 最近终于做完了Effective Java的读书笔记, 发布出来与大家共享. ...

  6. Effective Java 读书笔记之一 创建和销毁对象

    一.考虑用静态工厂方法代替构造器 这里的静态工厂方法是指类中使用public static 修饰的方法,和设计模式的工厂方法模式没有任何关系.相对于使用共有的构造器来创建对象,静态工厂方法有几大优势: ...

  7. Effective Java 读书笔记之二 对于所有对象都通用的方法

    尽管Object是一个具体的类,但设计它主要是为了扩展.它的所有非final方法都有明确的通用约定.任何一个类在override时,必须遵守这些通用约定. 一.覆盖equals时请遵守通用的约定 1. ...

  8. Effective Java 读书笔记(二):对象通用方法

    1 重写equals方法时请遵守通用约定 (1)无需覆盖equals方法的情况 要求独一无二 不要求逻辑相等 超类已经覆盖equals方法,对其子类也适用 一个类是私有的或者是包私有(可以重写后抛出异 ...

  9. Effective Java读书笔记——第三章 对于全部对象都通用的方法

    第8条:覆盖equals时请遵守通用的约定 设计Object类的目的就是用来覆盖的,它全部的非final方法都是用来被覆盖的(equals.hashcode.clone.finalize)都有通用约定 ...

  10. [Effective Java 读书笔记] 第三章 对所有对象都通用的方法 第八 ---- 九条

    这一章主要讲解Object类中的方法, Object类是所有类的父类,所以它的方法也称得上是所有对象都通用的方法 第八条 覆盖equals时需要遵守的约定 Object中的equals实现,就是直接对 ...

随机推荐

  1. HIVE部署安装(笔记)

    1.下载hive:wget http://mirrors.cnnic.cn/apache/hive/hive-0.12.0/hive-0.12.0.tar.gz2.解压hive安装文件 tar -zv ...

  2. MYSQL 表中汉字写入或字段赋值时乱码情况排误

    -- 当改动字段值.或是直接写入时,汉字变成乱码情况 .[可注意一下数据库名,记得改动] -- 当字符顺序对汉字不兼容时,可能直接导致乱码情况发生. 最好做到库.表.字段(字符类型)排序规则是否一致 ...

  3. Java+FlashWavRecorder实现网页录音并上传

    [注意] 最新版本号请看这里:http://uikoo9.com/blog/detail/java-flashwavrecorder [前言] 肯定有需求要网页录音,并且要上传.这奇葩需求. 然后找到 ...

  4. DataGrid前台数据绑定技巧

    (1)DataGrid控件不换行,数据显示不完全后面加"..." <%# DataBinder.Eval(Container.DataItem,? DataBinder.Ev ...

  5. UML 之 数据流图(DFD)

          数据流图(Data Flow Diagram):简称DFD,它从数据传递和加工角度,以图形方式来表达系统的逻辑功能.数据在系统内部的逻辑流向和逻辑变换过程,是结构化系统分析方法的主要表达工 ...

  6. Eclipse里如何配制项目在tomcat中启动

    首先,在Eclipse中新建一个Hello工程,Workspace的位置在c:/eclipse/workspace,所以hello工程的位置就是在%Workspace%/hello/这个文件夹中.  ...

  7. Java从零开始学三十五(JAVA IO- 字节流)

    一.字节流 FileOutputStream是OutputStream 的直接子类 FileInputStream也是InputStream的直接子类 二.文本文件的读写 2.1.字节输入流 Test ...

  8. _PyUnicodeUCS4_AsDefaultEncodedString

    "_PyUnicodeUCS4_AsDefaultEncodedString"的出现一般源于你在两个地方分别装了python,两个分别用UCS2和UCS4编码进行的build. 解 ...

  9. IDE、SATA、SCSI、SAS、FC、SSD硬盘类型介绍

    参考于:http://blog.csdn.net/tianlesoftware/article/details/6009110 目前所能见到的硬盘接口类型主要有IDE.SATA.SCSI.SAS.FC ...

  10. Python 图形界面(GUI)设计

    不要问我为什么要用 Python 来做这种事,我回到“高兴咋地”也不是不可以,总之好奇有没有好的解决方案.逛了一圈下来,总体上来说,Python 图形界面有以下几个可行度比较高的解决方案. 1. py ...