代码坏味道原意是指代码中看起来让人不舒服的地方,需要依靠一个程序猿的直觉去判断,听起来是不是有点摸不着头脑?哈哈,其实也不用纠结,按照我的理解,代码坏味道其实也就是代码中不遵循代码规范的地方。
那么,什么是写代码时要遵循的规范呢?我感觉主要有以下几种:
1、无重复代码
2、函数和功能模块仅实现单一功能目标
3、隔离变化,集中修改
4、信息隐藏和接口化
大致有这么几种吧。
下面我们具体看一下代码中都有哪些坏味道,坏味道一般是不遵循上述几条规范的代码。
1、重复代码
这个就不用我说了吧,不遵循第一种,解决办法是把相同的代码抽出来放到领一个函数或类中去。使各个需要用到它地方都能重用它,哈哈,重用,这也是软件工程的目标之一嘛。
2、过长函数
这个主要是违背了第二条规范,一定要记住,我们编写的函数仅实现单一功能和目标,碰到过长的函数就把它分割成数个小函数,这应该成为程序猿的强迫症之一。因为,小函数能给我们的程序带来更好地解释能力、共享能力和选择能力。
3、过大的类
同过长函数
4、过长参数列
其实这个到没有违背规范,只是看着让人不爽,你想啊,当你看到有一个函数需要10几个参数的时候,是不是很蛋疼。所以啊,作为一个敬业的程序员,这绝对不能忍,那怎么解决呢?在面向对象的编程中我们可以把它那些参数放到一个对象中,然后把这个对象再传给函数。怎么样,这样看着是不是舒服多了。
5、发散式变化
发散式变化是指软件的可维护性不强,即当外界发生了变化时,你代码中需要修改的地方有很多。而这就违背了我们所说的第三条规范---隔离变化,集中修改。软件工程强调,在我们所编写的程序中,针对外界变化所有相应的修改都应该集中到单一类中。针对这个问题,我们可以把所有需要变化的地方集中到一个类中,这个地方可能要用到多态,映射或则一些典型的设计模式。当然啦,如果能够达到不修改代码的程序,那就更厉害了。这样,在修改代码的时候是不是简单多啦。
6、霰弹式修改
同发散式变化
7、依恋情结
依恋情结是指某个函数对另外一个类的兴趣高过自己所处类的兴趣。这种爱慕之情最通常的体现便是数据。无数次经验里,我们看到某个函数为了计算某个数值,从另一个函数那几乎调用了半打的取值函数。解决办法也很简单,就是把这个函数移到它想去的地方去。
8、数据泥团
同过长参数列
9、基本类型偏执
这个其实只是在代码中用了太多的基本类型数据,在面向对象的世界里一般会把有关联的一些基本类型给替换成对象。额。。。其实我感觉这个坏味道并不是太明显,除非是达到了过长参数列的情形。
10、平行继承体系
这种情况是类结构设计的不合理引起的,即每当你为某个类增加一个子类,也必须为另外一个类增加一个相应的子类时。如果有人看过headfirst设计模式的话应该就能很快理解,headfirst中一条很重要的准则便是要组合不要继承。即它希望类体系中出现尽量少的继承关系,而用组合关系去替代一些不太必要的继承。
11、冗余类
在软件维护中,你所创建的每一个类,都得有人去理解它,维护它,而这些工作都是要花钱的。因此,如果一个类的所得不值其身价,那就消除它。
12、夸夸其谈未来性
这个其实是我们在程序设计中额外的增加了一些类,目的是未来某一天我们可能会用到它。但是这会让系统难以理解和维护。因此,我觉得如果用不到,那就搬开它吧。这个其实有点像冗余类。
13、switch惊悚现身
面向对象的一个最明显的特征就是:少用switch语句。因为从本质上来说,switch语句的问题在于重复。就像重复代码一样,所以我们有必要去解决它。而面向对象也给我们提出了优雅的解决方法,那就是多态。
14、令人迷惑的暂时字段
有时你会看到这样的对象:其内某个实例变量仅为某种特定情况而设。这样的代码让人不易理解,因为你通常认为对象在所有的时候都需要它的所有变量。在变量未被使用的情况下猜测当初其设置目的,会让你发疯的。那我们就解决它,给这个可怜的孤儿创造一个新家,然后把和这个变量相关的代码都放到这个新家中。
15、过度耦合消息链
这样的代码往往造成代码的维护性较低,一旦对象间的关系发生任何变化,就需要修改很多地方。因此,我们应该为它松绑,也就是解耦合。
16、中间人
同隔离变化
17、狎昵关系
同过长函数