1.重复代码
将重复代码合而为一。Extract Method提炼重复代码,都调用这一个方法。
2.过长函数
间接层的好处:解释能力、共享能力、选择能力-------都是小型函数支持的
需要更积极地分解函数,并以其用途(而非实现方法)命名
如果函数有大量参数和临时变量,运用Replace TempQuery方法来消除(看到这里是蒙逼的,后面会有方法解释吧)。
条件表达式和循环也是需要提炼的信号
3.过大的类
如果类内数个变量名(意义)有着相同的前缀或者字尾,就可以把他们提炼到某个组件内,或者这个组件也可以作为子类。
如果这个大类是个GUI类,就可以把数据和行为部分分开(MVC,详见之前写的关于Pure MVC框架)。可能需要两边各保留一些重复数据,并保持两边同步。
4.过长的参数列
可以叫另一个对象给你。
5.发散式变化
我们希望软件能更容易被修改,一旦被修改,要做到只在该处修改。
如果一个类经常被修改,这就是发散式变化。
可以将对象分为两部分,需要修改的为一部分,不需要修改的为另一部分。Extract Class
6.散弹式修改
如果要修改某处,需要在很多地方修改,这就是散弹式修改。
可以将所有需要修改的代码放进同一个类/函数,如果无处可放就Inline Class做一个内部类。
7.依恋情结
OOP类:将数据和对数据的操作行为包装在一起。
依恋情结就是,函数对某个类的操作高于对自己类的操作。就要把这个函数放到那个类里Move Method
如果一个函数需要对几个类进行操作,可以把函数放到操作最多的类中,或者把函数拆分成几个小函数放到不同的类中。
最根本的原则是:将总是一起变化的东西放在一起。
策略模式和访问者模式破坏了这个原则,它们使你得以轻松修改函数行为,因为它们将少量需要被覆写的行为隔离开来---也多了“多一层间接性”的代价
8.数据泥团
在很多地方看到相同的数据,就需要将他们提炼到一个对象中调用。
减少字段和参数的个数,当然可以去除一些坏味道。
9.基本类型偏执
结构类型数据允许你将数据组织成有意义的形式(对象,类,结构体,数据库的表)
基本类型则是构成结构类型的积木块。
对象的一个价值在于:它们模糊(甚至打破)了基本数据和体积较大的类之间的界限。可以写一些内部类小型类等。
有的人不愿意在小任务上运用小对象(像是vector ,rect等等,虽然在Unity中这个是结构体,不过结构体也一样),可以把数据替换为对象,甚至大可以把这些对象作为数据。
10.switch惊悚现身
switch语句的问题在于重复。可以用oop的多态来解决
将switch语句提炼到一个独立的函数中Extract Method,在Move Method搬移到需要多态性的那个类里,再决定是否使用Replace Type Code With Subclasses 或者 Replace Type Code With State/Strategy,完成了继承结构后,就可以运用 Replace Conditional with Polymorphism了。(这块没看明白,这些方法在后面再看一遍)
扩充:消除switch的方法,可以用反射,或者Dictionary<key,Method>的方法来处理
利用多态取代switch其实是一种面向对象的编程思想
11.平行继承体系
当为一个类增加一个子类时,也必须要为另一个类增加一个子类。
让一个继承体系的实例引用另一个继承体系的实例。
12.冗赘类
对于几乎没用的组件,应该Inline Class作为内部类。
13.夸夸其谈未来性
过于为未来着想,加了许多不必要的抽象和钩子。
如果某个抽象类其实没有太大作用,就用 collapse Hierarchy。不必要的委托就用Inline Class内部类来除掉。去除函数中不必要的参数,并修正函数名。
如果有这样的函数或类,就把其测试用例也一并删掉。
14.令人迷惑的暂时字段
为特定情况而设的变量(不常用,且不易懂)归到同一个新类中
15.过度耦合消息链
当某个变量向一个对象请求另一个对象,再请求另一个对象等等,这就是消息链,一长串getThis()。这导致代码紧密耦合,一旦对象间关系发生变化,就需要大量修改。
可以将这一系列对象变成中间件,将他们提炼到一个新函数中。
16.中间件
封装与委托
如果一个类有超过一半的函数都委托给中间件,这就是过度运用,应该去掉这个中间件。
17.狎昵关系
两个类过于操作对方的private部分。
可以把互相用到的部分还给对方,或者把他们的共同部分提炼到一个新的类。或者Hide Delegate(这个也要到后面才能知道是什么)
18.异曲同工的类
两个函数功能相同名字不同。只保留一个并且重新命名。
19.不完美库类
修改库的函数,就用旧函数调用新函数。
20.纯稚的数据类
类似容器的类(ICollection .Net容器),要用Encapsulate Collection把他们封装起来(要看后面)
21.拒绝的遗赠
子类如果不想继承所有父类
说明继承体系设计错误。
22过多的注释
注释过长,说明代码很糟糕,让人看不懂。
或者提炼出新的函数进行功能说明