码农的自我修养-对编写简洁代码的理解

来源:互联网 发布:空军知乎 编辑:程序博客网 时间:2024/06/05 12:18

笔者惯用的开发语言是C++,和大多软件发人员一样,有代码整洁强迫症。看到一句代码没对齐,看到一个变量命名不考究,总想动一下;看到逻辑混乱的代码也会从心底发出一句Shit ! 当然,绝大多数情况还是克制一下,总要尊重一下代码作者的著作权,要考虑修改对版本造成的风险。

 

 对于我自己编写代码,平时看到不爽的地方,或者函数职责不单一,或者函数名,类名,变量名未表达清楚,在确认不大会引入问题的情况下还是经常忍不住会动一动。它们也许是我在最初编写的时候抢时间,也许当时还是没有考虑得很清楚就下手了,也可能是在维护过程中其他人在没有理解全局代码逻辑情况下加的一个“特殊处理”。在维护改Bug时或者是在新版本增加新特性时就是重构的最好时候。

 

所谓简洁的代码含义很广泛,下面只是从如果编写一个简洁的函数说一下我的理解:

 

1:整洁的函数是增一分太肥,减一分太瘦的。

SOLID原则第一条就是单一职责原则。设计模块要求职责单一、类要职责单一、函数要职责单一。函数作为贯彻单一职责原理的最小单元,它表达的含义应该是逻辑上独立、内聚的单元。我在检视代码的过程中经常发现两种问题:

 

1) 万能函数 所有的功能都柔和在一起,看这种函数你只想用一个量词来描述它 一坨”。

2) 割裂函数 很单一的功能被分拆到两个或者多个函数中,看的时候有一种精神分裂的错觉。

 

对于第一种情况很多时候开发人员就是记流水账,没有分拆的意思,就好像我们小学最开始写作文时的一样,就一段;对于第二种情况很多时候是撇脚的重构导致的--QA代码审查发现大函数要求开发人员分拆,开发人员说:好吧,数着函数行数多少行拆成一个。然后...,然后把是一条蚯蚓随意的砍成几段。造孽啊。

 

所以在写函数时一定要考虑函数逻辑上的内聚性。把大函数拆成小函数很容易,把逻辑相关的代码分离清楚很难。

 

2:简洁的函数是最小依赖的。

 按函数的定义y=f(x)表示值域到解域的映射。函数执行的结果仅依赖于它的输入,函数的执行结果仅反映它的输出。在输入保持不变的情况下,函数执行任意多次返回结果都应该是不变的。

 

如果函数执行依赖全局变量作为输入或者执行过程中改变了全局变量的值,它都是不满足严格函数定义的。比如一个功能是从账户中取款并返回账户余额的函数,每次输入取款额100元,返回的余额逐渐减少。它依赖于账户余额这个全局变量,它不是最小依赖。

 

对外部依赖过强的函数扩展性,移植性,可测试性都比较差。当我们在设计功能函数时有外部依赖时可以考虑是否可以将这些依赖的数据作为输入参数传入。

 

3:整洁的函数是条例清晰、思路连贯的。

维护过程中经常因遇到锯齿状、流水账式的代码而感到眩晕。当你看到这样的代码时请相信写代码的人脑袋比你还晕。看代码的逻辑就知道作者写这些代码时思路是多么的混乱,就是想到哪写到哪。

 

如果写代码前业务没搞清楚,逻辑没理清,请搞清楚了再编码。如果是加班太过疲惫,休息调整一下状态再编码。务必要留给后人一个清晰,有条理的代码世界。

 

4:编写简洁的函数有时得靠直觉。

判断一个函数职责是否单一,设计是否合理,代码是否优雅的能力很多时候是要靠经验积累、不断学习思考、不断总结,不断练习提升上来的,有时也要靠直觉来判断。各种编程规范、代码度量标准只是保证新员工不写出太烂的代码,而没有方法能教人写出优秀的代码,就好像能教人绘画技巧,钢琴技巧,却没有办法教人如何成为达芬奇,贝多芬一样。