第1部分 面向对象编程初级篇 3
第1章 面向过程编程和面向对象编程 3
1.1 什么是面向过程编程 3
1.2 什么是面向对象编程 4
1.2.1 什么是对象 4
1.2.2 什么是类 4
1.2.3 什么是统一建模语言 6
1.3 面向过程编程有哪些局限性 9
1.4 面向对象编程有哪些优点 13
第2章 MATLAB面向对象编程入门 16
2.1 如何定义一个类 16
2.2 如何创建一个对象 17
2.3 类的属性 19
2.3.1 如何访问对象的属性 19
2.3.2 什么是属性的默认值 19
2.3.3 什么是常量属性 21
2.3.4 什么是非独立属性 21
2.3.5 什么是隐藏属性 25
2.4 类的方法 26
2.4.1 如何定义类的方法 26
2.4.2 如何调用类的方法 27
2.4.3 点调用和函数调用类方法的区别 29
2.4.4 什么是方法的签名 29
2.4.5 类、对象、属性和方法之间的关系 32
2.4.6 如何用disp方法定制对象的显示 32
2.5 类的构造函数 35
2.5.1 什么是构造函数 35
2.5.2 如何在构造函数中给属性赋值 36
2.5.3 如何让构造函数接受不同数目的参数 36
2.5.4 什么是默认构造函数 37
2.5.5 用户一定要定义构造函数吗 38
2.6 类的继承 39
2.6.1 什么是继承 39
2.6.2 为什么子类构造函数需要先调用父类构造函数 43
2.6.3 在子类方法中如何调用父类同名方法 45
2.6.4 什么是多态 46
2.7 类之间的基本关系:继承、组合和聚集 47
2.7.1 如何判断B能否继承A 47
2.7.2 企鹅和鸟之间是不是继承关系 48
2.7.3 如何把类组合起来 49
2.7.4 什么是组合聚集关系 51
2.8 Handle类的set和get方法 52
2.8.1 什么是set方法 52
2.8.2 什么是get方法 54
2.9 类的属性和方法的访问权限 56
2.9.1 什么是public、protected和private权限 56
2.9.2 如何设置类的属性和方法的访问权限 59
2.9.3 如何更细粒度地控制访问权限 60
2.9.4 MATLAB对属性访问的控制与C++和Java有什么不同 62
2.10 clear classes到底清除了什么 63
2.11 对象根据类定义的改变而自动更新 64
第3章 MATLAB的句柄类和实体值类 66
3.1 引子:参数是如何传递到函数空间中去的 66
3.2 MATLAB的Value类和Handle类 70
3.2.1 什么是Value类和Handle类 70
3.2.2 Value类对象和Handle类对象复制有什么区别 72
3.2.3 Value类对象和Handle类对象赋值有什么区别 73
3.2.4 Value类对象和Handle类对象当作函数参数有什么区别 76
3.2.5 Value类对象和Handle类对象作为默认值有什么区别 77
3.2.6 什么情况下使用Value类或Handle类 78
3.3 类的析构函数(Destructor) 83
3.3.1 什么是对象的生存周期 83
3.3.2 什么是析构函数 84
3.3.3 对Object使用clear会发生什么 84
3.3.4 对Object使用delete会发生什么 85
3.3.5 什么情况下delete方法会被自动调用 88
3.3.6 出现异常时delete函数如何被调用 91
3.3.7 什么情况下用户需要自己定义一个delete方法 92
第4章 事件和响应 95
4.1 事件 95
4.1.1 什么是事件 95
4.1.2 如何定义事件和监听事件 96
4.1.3 为什么需要事件机制 97
4.2 发布者通知观察者,但不传递消息 98
4.3 发布者通知观察者,并且传递消息 100
4.4 删除listener 103
第5章 MATLAB类文件的组织结构 104
5.1 如何使用其他文件夹中类的定义 104
5.2 如何把类的定义和成员方法的定义分开 105
5.3 如何定义类的局部函数 106
5.4 如何使用Package文件夹管理类 108
5.4.1 Package中的类是如何组织的 108
5.4.2 如何使用Package中的某个类 109
5.4.3 如何导入Package中的所有类 109
5.5 函数和类方法重名到底调用谁 109
5.6 Package中的函数和当前路径上的同名函数谁有优先级 110
第6章 MATLAB对象的保存和载入 112
6.1 save和load命令 112
6.1.1 对象的save和load操作 112
6.1.2 MAT文件中保存了对象中的哪些内容 112
6.1.3 如果类的定义在save操作之后发生了变化 116
6.2 saveobj和loadobj方法 118
6.2.1 如何定义saveobj方法 118
6.2.2 如何定义loadobj方法 119
6.3 继承情况下的saveobj和loadobj方法 120
6.3.1 存在继承时如何设计saveobj方法 120
6.3.2 存在继承时如何设计loadobj方法 122
6.4 什么是瞬态属性 123
6.5 什么是装载时构造(ConstructOnLoad) 125
第7章 面向对象的GUI编程:分离用户界面和模型 127
7.1 如何用GUIDE进行GUI编程 127
7.2 如何用面向过程的方式进行GUI编程 129
7.3 如何用面向对象的方式进行GUI编程 132
7.4 模型类中应该包括什么 134
7.5 视图类中应该包括什么 135
7.6 控制器类中应该包括什么 138
7.7 如何把Model、View和Controller结合起来 139
7.8 如何测试MVC的GUI程序 141
7.9 如何设计多视图的GUI以及共享数据 142
7.10 如何设计GUI逻辑 架构 147
7.11 如何使用GUI Layout Toolbox对界面自动布局 151
7.11.1 为什么需要布局管理器 151
7.11.2 纵向布局器VBox类 152
7.11.3 横向布局器HBox类 154
7.11.4 选项卡布局器TabPanel类 155
7.11.5 网格布局器Grid类 156
7.11.6 GUI Layout的复合布局 157
7.11.7 把GUI Layout Toolbox和MVC模式结合起来 158
7.11.8 GUI Layout Toolbox两个版本的说明 160
第2部分 面向对象编程中级篇 163
第8章 类的继承进阶 163
8.1 继承结构下的构造函数和析构函数 163
8.1.1 什么情况需要手动调用基类的构造函数 163
8.1.2 什么情况可以让MATLAB自动调用基类的构造函数 164
8.1.3 常见错误:没有提供默认构造函数 166
8.1.4 在构造函数中调用哪个成员方法 167
8.1.5 析构函数被调用的顺序是什么 168
8.2 MATLAB的多重继承 169
8.2.1 什么情况下需要多重继承 169
8.2.2 什么是多重继承 170
8.2.3 构造函数被调用的顺序是什么 172
8.2.4 多重继承如何处理属性重名 172
8.2.5 多重继承如何处理方法重名 174
8.2.6 什么是钻石继承 175
8.2.7 如何同时继承Value类和Handle类 178
8.3 如何禁止类被继承 180
第9章 类的成员方法进阶 182
9.1 Derived类和Base类同名方法之间有哪几种关系 182
9.1.1 Derived类的方法覆盖Base类的方法 182
9.1.2 Derived类的方法可以扩充Base类的同名方法 183
9.1.3 Base类的方法可以禁止被Derived类重写 184
9.2 什么是静态方法 184
9.3 同一个类的各个对象如何共享变量 186
9.3.1 什么情况下各个对象需要共享变量 186
9.3.2 如何共享Constant属性 186
9.3.3 如何共享变量 187
第10章 抽象类 189
10.1 什么是抽象类和抽象方法 189
10.2 为什么需要抽象类 190
10.3 如何使用抽象类 191
10.3.1 抽象类不能直接用来声明对象 191
10.3.2 子类要实现所有的抽象方法 192
第11章 对象数组 195
11.1 如何把对象串接成数组 195
11.2 如何直接声明对象数组 196
11.3 如何使用findobj函数寻找特定的对象 199
11.4 如何利用元胞数组把不同类的对象组合到一起 201
11.5 什么是转换函数 203
11.6 如何利用转换函数把不同类的对象组合到一起 204
11.7 如何用非同类(Heterogeneous)数组盛放不同类对象 205
11.7.1 为什么需要非同类数组 205
11.7.2 含有不同类对象的数组类型 207
11.7.3 使用非同类要避免哪些情况 209
11.7.4 如何向量化遍历数组中对象的属性 209
11.7.5 如何设计成员方法使其支持向量化遍历 211
第12章 类的运算符重载 213
12.1 理解MATLAB的subsref和subsasgn函数 213
12.1.1 MATLAB如何处理形如a(1,:)的表达式 213
12.1.2 MATLAB如何处理形如a{1,:}的表达式 214
12.1.3 MATLAB如何处理形如s.f的表达式 215
12.2 如何重载subsref函数 216
12.3 如何重载subsasgn函数 217
12.4 什么情况下重载下标运算符 218
12.5 如何重载plus函数 219
12.6 MATLAB的Dispatching规则是什么 220
12.7 如何判断两个对象是否相同 221
12.8 如何让一个对象在行为上像一个函数 223
12.9 MATLAB中哪些运算符允许重载 226
12.10 实例:运算符重载和量纲分析 227
12.10.1 如何表示量纲 227
12.10.2 需求和设计:加法和减法 229
12.10.3 需求和设计:乘法和除法 232
第13章 枚举类型 237
13.1 为什么需要枚举类型(Enumeration) 237
13.2 什么是枚举类型 241
13.3 枚举类型应用实例 243
13.3.1 枚举类型的属性 243
13.3.2 枚举类型的方法 244
13.3.3 枚举类型对象数组 246
13.3.4 从基本数据类型中派生枚举类型 247
第14章 超类 249
14.1 什么是超类 249
14.2 如何获得一个类的meta.class对象 250
14.3 meta.class对象中有些什么内容 252
14.4 如何手动克隆一个对象 253
14.5 如何使用matlab.mixin.Copyable自动克隆一个对象 259
第3部分 设计模式篇 265
第15章 面向对象程序设计的基本思想 265
15.1 单一职责原则 266
15.2 开放与封闭原则 268
15.3 多用组合少用继承原则 269
15.4 面向接口编程 271
第16章 创建型模式 276
16.1 工厂模式:构造不同种类的面条 276
16.1.1 简单工厂模式 276
16.1.2 工厂模式 280
16.1.3 工厂模式总结 282
16.1.4 如何进一步去掉switch/if语句 283
16.1.5 抽象工厂 285
16.1.6 抽象工厂模式总结 287
16.2 单例模式:给工程计算添加一个LOG文件 288
16.2.1 如何控制对象的数量 288
16.2.2 如何删除一个Singleton对象 290
16.2.3 应用:如何包装一个对象供全局使用 291
16.3 建造者模式:如何用MATLAB构造一辆自行车 293
16.3.1 问题的提出 293
16.3.2 应用:建造者模式为大规模计算做准备工作 297
16.3.3 建造者模式总结 298
第17章 装饰者模式 302
17.1 装饰者模式的引入 302
17.2 面馆菜单代码 304
17.3 装饰者模式总结 306
第18章 行为模式 308
18.1 观察者模式:用MATLAB实现观察者模式 308
18.1.1 发布和订阅的基本模型 308
18.1.2 订阅者查询发布者的状态 311
18.1.3 把发布者和订阅者抽象出来 312
18.1.4 观察者模式总结 313
18.2 策略模式:分离图像数据和图像处理算法 316
18.2.1 问题的提出 316
18.2.2 应用:更复杂的分离数据和算法的例子 320
18.2.3 策略模式总结 321
18.3 遍历器模式:工程科学计算中如何遍历大量数据 323
18.3.1 问题的提出 323
18.3.2 聚集和遍历器 324
18.3.3 遍历器模式总结 328
18.4 状态模式:用MATLAB模拟自动贩卖机 329
18.4.1 使用if语句的自动贩卖机 329
18.4.2 使用状态模式的自动贩卖机 335
18.4.3 状态模式总结 340
18.5 模板模式:下面条和煮水饺有什么共同之处 341
18.5.1 抽象下面条和煮水饺的过程 341
18.5.2 应用:把策略和模板模式结合起来 346
18.5.3 模板模式总结 347
18.6 备忘录模式:实现GUI的undo功能 348
18.6.1 如何记录对象的内部状态 348
18.6.2 应用:如何利用备忘录模式实现GUI的do和undo操作 351
18.6.3 备忘录模式总结 356
第4部分 框架篇 359
第19章 MATLAB单元测试框架 359
19.1 框架概述 359
19.2 基于函数的单元测试构造 359
19.3 getArea函数的单元测试:版本Ⅰ 361
19.4 getArea函数的单元测试:版本Ⅱ和版本Ⅲ 366
19.5 测试的准备和清理工作:Test Fixture 369
19.6 验证方法:Types of Qualification 371
19.7 测试方法论和用测试驱动开发 375
19.7.1 开发流程概述 375
19.7.2 用测试驱动开发:fibonacci例 377
19.7.3 用测试驱动开发:运算符重载和量纲分析 381
19.8 基于类的单元测试 393
19.8.1 getArea函数的基于类的单元测试 393
19.8.2 MVC GUI的基于类的单元测试 395
第20章 MATLAB性能测试框架 401
20.1 为什么需要MATLAB性能测试框架 401
20.2 基于类的性能测试框架 403
20.2.1 构造测试类 403
20.2.2 测试结果解析 405
20.3 误差范围和置信区间 407
20.4 性能测试的适用范围讨论 410
附录 413
附录A 综合实例:如何把面向过程的程序转成面向对象的程序 413
附录B MATLAB高级数据结构:containers.Map 425
B.1 containers.Map简介 425
B.2 数组、元胞数组和结构体的局限性 426
B.3 用containers.Map来记录电话号码簿 428
B.4 containers.Map的属性和成员方法 429
B.5 containers.Map的特点 430
B.5.1 containers.Map可以不断地扩张且不需要预分配 430
B.5.2 containers.Map可以作为参数在函数内部直接修改 431
B.5.3 containers.Map可以增强程序的可读性 431
B.5.4 containers.Map提供对数据的快速查找 431
B.6 containers.Map的使用实例 433
B.6.1 用来存放元素周期表 433
B.6.2用来实现快速检索 433
附录C MATLAB高级数据结构:table 435
C.1 table简介 435
C.1.1 为什么需要table数据结构 435
C.1.2 通过导入数据构造table对象 436
C.1.3 调用table构造函数来构造table对象 436
C.1.4通过转换函数构造table对象 437
C.2 访问table中的数据 438
C.3 table的操作 439
C.3.1 删除行列 439
C.3.2 添加行列 440
C.3.3合并table 441
C.3.4操作列数据 442
C.3.5排序 444
C.3.6筛选和查找 445
C.3.7输出到文件 445
C.4 其他数据类型之间和table相互转换 446
C.5 table之间的操作 449
C.6 table的属性和支持的操作 452
附录D 对函数的输入进行检查和解析 454
D.1 为什么要对函数的输入进行检查 454
D.2 validateattributes 454
D.2.1 validateattributes的基本使用 454
D.2.2 validateattributes的额外提示信息 455
D.2.3 validateattributes支持的检查类型和属性 457
D.3 validatestring 458
D.4 inputParser 459
D.4.1 inputParser的基本使用 459
D.4.2 inputParser的可选参数和默认参数值设置 461
D.4.3 inputParser和validateattributes联合使用 462
D.4.4 inputParser的参数名-参数值对的设置 462
D.4.5 inputParser解析结构体的输入 465
D.5 引子:为什么需要MATLAB的单元测试系统 466
参考文献 468
写在最后 469