8 面向对象
描述
对象
一件事、一个实体、一个名词、可以获得的某种东西、可以想象有自己标志的任何东西
对象有attribute属性、behavior行为(不一定是有生命的对象才有行为)
anObject |
attribute1 attribute2 |
operation1() operation2() |
对象1==对象2,是对象的标识符比较,如果两个对象相同返回true
对象1.equals(对象2),是对象的值比较,如果两个对象的值相同返回true
类
类是对象的封装
anObject |
attribute1 attribute2 |
operation1() operation2() |
关系
关联 association
(箭实线),对应关系,A指向B,B=A变量的值
依赖 dependency
(箭虚线),调用关系,A指向B,B=A方法的形参
依赖关系 | 功能 | 关键字 |
---|---|---|
访问 | 允许一个包访问另一个包的内容 | access |
绑定 | 为模板参数绑定值,以生产一个新的模型元素 | bind |
调用 | 声明一个雷调用其他类的操作的方法 | call |
导出 | 声明一个实例可从另一个实例导出 | derive |
友员 | 允许一个元素访问另一个元素,不管能访问的元素是否具有可见性 | friend |
引入 | 允许一个包访问另一个包的内容并为被访问的组成部分添加别名 | import |
实例化 | 关于一个类的方法创建了另一个雷的实例的声明 | instantiation |
参数 | 一个操作和他的参数之间的关系 | parameter |
实现 | 说明和其实之间的隐射关系 | realization |
精化 | 声明具有两个不同语义层次上的元素之间的映射 | refine |
发送 | 信号发送者和信号接受者之间的关系 | send |
跟踪 | 声明不同类型中的元素之间存在一些联系,但不如映射精准 | trace |
使用 | 声明使用一个模型元素需要用到已存在的另一个模型元素,这样才能正确实现使用者的功能(包含调用、实例化、参数、发送) |
聚合 aggregation
(空菱线),弱拥有,B菱指A,B=A成员变量,B可独立存在
在汽修店的业务环境中,汽车和轮胎就是聚合的关系,轮胎离开汽车是有业务意义的。
组合 composition
(实菱线),强拥有,B菱指A,B=A成员变量,B在A构造函数初始化
在车主买汽车这个业务中,轮胎和汽车是组合关系,它们分开就没有实际意义了。
泛化 generalization
(角实线),子类 继承 父类,角指父类
实现 realization
(角虚线),类 实现 接口,角指接口
封装
数据
隐藏:同一层的对象之间,数据对彼此是隐藏的
方法
隐藏:各类都有自己的实现方法
对象
隐藏:除了组合/聚合的整体类对象,其他对象对其组成部分一无所知
类型
隐藏:通过多态使用抽象类,abstract/interface
Is a(能力一次继承)abstract class有可修改的数据成员、有abstract/非abstract方法(默认行为)
Like a(能力多重继承)interface有static final数据成员、有abstract方法(无默认行为)
变化
方式一:基类=>泛化类(派生类) =>特化类(派生类的子类)
方式二:对行为变化进行分类,即发现变化并将其封装
数据变化:增加成员变量
行为变化:
相对性状二个选一:一个类,变量标志行为,方法内判断执行
相对性状二个任选:一个类,两个方法各自执行
相对性状一个固定:三个类,一个基类两个派生
多对性状多个任选:整体-部分的组合/聚合
覆盖(内变)
方法名相同,形参相同,实现方式不同
重载(外变)
方法名相同,形参不同,实现方式不同
原则
OCP开闭
开放扩展,关闭修改。即将软件设计成不用修改就能扩展功能。
DIP依赖倒置
针对接口编程,依赖于抽象而不依赖于具体。
ISP接口隔离
使用多个隔离接口,比单个接口要好
CRP合成复用
尽量组合/聚合,而不是用继承
LSP里氏替换
基类出现的地方,子类也能出现。派生类可以替换基类,基类才能真正被复用。
DP最少知道
实体应当尽少于其他实体相互作用
视角
方式一(层次太多):问题域->名词->对象->名词相关动词->对象添加方法
方式二:共性和可变性分析,找出变化并封装->聚集优先于继承->对接口编程优于对实现编程
概念视角
共性分析:设计抽象类,在问题领域必须完成哪些基本操作
规约视角
向上如何实现共性,向下如何实现可变性,一般是继承抽象类/实现接口
实现视角
可变性分析:设计派生类,特定情况的实现