高质量代码精品资源推荐(十三)---如何编写高质量的代码_编码规范
[复制链接]
如何编写高质量的代码_编码规范
软件的首要技术使命是管理复杂度,计算先驱Edsger Dijkstra指出,只有在“计算(Computing)”这种职业中,人的思维需要从一个字节大幅跨越到几百兆字节——跨度为109比1,也就是9个数量级[1]。Dijkstra还指出,没有谁的大脑能容得下一个现代的计算机程序,也就是说,作为软件开发人员,我们不应该试着在同一时间把整个程序都塞进自己的大脑,而应该试着以某种方式去组织程序,以便能够在一个时刻可以专注于一个特定的部分。这么做的目的是尽量减少在任一时间所要考虑的程序量,你需要同时记住的东西越多,就越可能漏掉其中的某一个,从而导致设计或编码的错误。 尽管谁都希望成为英雄,自如地应对各种计算机问题,但没有人的大脑真正有能力同时掌握9个数量级的细节。计算机科学和软件工程已经开发了许多智力工具,来应对这种复杂度,《代码大全》围绕这一主题作了详尽的讨论。 ■ 在架构层将系统划分为多个子系统,以便让思绪在某段时间内能专注于系统的一小部分。(第5章) ■ 仔细定义类接口,从而可以忽略类内部的工作机理。(第6.1节) ■ 保持类接口的抽象性,从而不必记住不必要的细节。(第6.2节) ■ 避免全局变量,因为它会大大增加总是需要兼顾的代码比例。(第13.3节) ■ 避免深层次的继承,因为这样会耗费很大精力。(第6.3节) ■ 避免深度嵌套的循环或条件判断,因为它们都能用简单的控制结构取代,后者占用较少的脑力资源。(第19.4节) ■ 别用goto语句,因为它们引入了非顺序执行,多数人都不容易弄懂。(第17.3节) ■ 小心定义错误处理的方法,不要滥用不同的错误处理技术。(第8.3节) ■ 以系统的观点对待内置的异常机制,后者会成为非线性的控制结构。异常如果不受约束地使用,会和goto一样难以理解。(第8.4节) ■ 不要让类过度膨胀,以至于占据整个程序。(第6章) ■ 子程序应保持短小。(第7.4节) ■ 使用清楚、不言自明的变量名,从而大脑不必费力记住诸如“i代表账号下标,j代表顾客下标,还是另有它意?”之类的细节。(第11章) ■ 传递给子程序的参数数目应尽量少。更重要的是,只传递保持子程序接口抽象所必需的参数。(第7.5节) ■ 用规范和约定来使大脑从记忆不同代码段的随意性、偶然性差异中解脱出来。(第4.2节,第31、32章) ■ 只要有可能,一般情况下应避免“偶然性困难”。 如果将复杂的逻辑判断代码放入布尔函数,并将其意图概括出来,就可以降低代码的复杂程度。用查表法代替繁琐的逻辑链,也能达到同样目的(第18章)。如果采用定义良好的一致的类接口,你就无须操心类的实现细节,从而整体上简化自己的工作。 采用编码规范主要也是为了降低复杂度。如果在格式编排、循环、变量命名、建模表示法等方面有统一的考虑,就能将精力集中于更具挑战性的编码问题上。规范最有用之处在于它们能免于你做出任意决定,省却了为之辩解的麻烦。 各种形式的抽象对于管理复杂度都是很强大的工具。通过增强程序组件的抽象性,编程领域已经取得了很大的进步。Fred Brooks指出,计算机的科学最了不起的成就,就是从机器语言跃进到高级语言,解放了程序员——我们不用再操心某种特定的硬件细节,而能够专心于编程。子程序的想法则是另一个巨大的进步,随后的重要进步是类和程序包。 以其功能对变量命名,说明问题是什么,而非其怎样实现,能提升其抽象层次。如果你说:“这是弹出栈,意味着我在取最近雇员的信息”,那么抽象使你可以省掉记住“弹出栈”的脑力步骤,你只需简单地说“我在取最近雇员的信息。”这一长进是微不足道的,但当你要减少从1到109这么大范围的复杂度时,任何改进措施都是值得的,勿以善小而不为。采用具名常量而非文字量(神秘数值)也能提高抽象级别。面向对象的编程方法提供同时适用于算法和数据的抽象,单靠功能分解做不到这一点。 总而言之,软件设计与构建的主要目标就是征服复杂度。许多编程实践背后的动机正是为了降低程序的复杂度。降低复杂度几乎是衡量程序员成果的最重要依据。这是《代码大全》体现的最主要的编程思想。(虽然这本书从头至尾没有正式提到过“编程思想”这个词。)
|