可复用性:
代码层面:方法
模块层面:类和接口
库层面:API
系统级别复用:framework(框架)
继承:子类可以完成父类所有功能,此外还可以进行扩展、重写(override)
白盒框架:代码层面的继承,进行框架扩展
黑盒框架:通过实现特定接口,通过delegation(委派)进行框架拓展。
在任何能用父类场景都可以用子类不会产生任何问题。
LSP:
子类可以增加方法但不能删除。
子类实现抽象类中所有未实现的方法。
子类中重写的方法必须有相同/协变返回值 如父类返回值object子类String,可以理解为返回值子类更具体
子类中重写的方法必须有相同/逆变参数,可以理解为参数子类更抽象
子类override方法不能抛出额外的异常
子类spec条件:更强的不变量,更弱的前置条件,更强的后置条件。
object中缺省的equals判断引用等价性,需要重写。
严格说没有AF不能直接equals判断每个域的等价性
除非对象被修改否则调用equals多次应该结果相同。
x.equals(null)若x不空直接返回false
equals为true的两个对象hashcode()结果必须一致。
等价需要自反性 对称性 传递性 尤其是传递性。
mutable对象等价性分为行为等价性和观察等价性。
== 引用等价性 对基本数据类型
equals 对象等价性 对对象类型
行为等价性:看内存地址(调用对象任何方法,包括mutator和observer有相同结果)
观察等价性:不改变状态情况下是否“看起来一致”,比较内容,即看observer结果是否一致
CRP:
使用接口定义系统对外展示的不同侧面的行为
接口之间通过extends实现行为拓展(接口的组合)
类实现组合接口从而规避复杂的继承关系
更多的使用委派和组合,看场合尽量少用继承
临时性delegation:通过方法参数建立起来的关系,即A use B
Association:永久的delegation,委派通过固有field建立
composition:更强的Association,难以变化
Aggregation:更弱的association,可以动态变化