《程序员修炼之道》读书笔记(2):注重实效的途径(道理)

第2章:注重实效的途径

这一章讲的是:

通用于软件开发各个层面的道理,包括:

  • 不要有重复的内容
  • 让你的设计有正交性
  • 让你的决定有可撤销性
  • 开发一个新工程时先写好直达核心功能的部分,之后再往上面加内容
  • 制作原型以实验不确定的内容
  • 使用特定领域的专门语言更容易找到方案
  • 练习估算能力使你能快速知道一个方案的可行性

7《重复的危害》

系统中的每一项知识都必须具有单一、无歧义、权威的表示
简称为DRY(Don’t Repeat Yourself)

否则,当一个知识需要变化时,就需要改动多处,假如没有改全则会造成矛盾。

这算是最重要的道理之一

大多数重复都可归为如下范畴:

强加的重复

——开发者觉得他们别无选择,因为环境似乎要求重复。

例如:

  • 代码中表示了一遍知识,随后文档又描述了一遍相同的内容。
  • 多个平台需要各自的编程语言,开发环境。
  • 编程语言自身要求某些重复信息的结构。

这种重复相对不容易解决,但是发挥聪明才智可以解决一部分。
一些方法例如:

  • 抽象出重复的东西以公用。
  • 代码生成器。
  • 根据代码自动生成文档的生成器。

无意的重复

——开发者没有意识到他们在重复信息。

此种情况多缘于设计上的错误。

无耐性的重复

——开发者偷懒,他们重复是因为这样更容易。

这经常缘于项目的时间压力。

这种重复相对容易检测出来。
不过需要你愿意为避免以后的痛苦而现在花费一些时间。

开发者之间的重复

——同一团队(或不同团队)的几个人重复了同样的信息。

这个较难检测和处理。

在团队的高层,领导应通过清晰的设计和强有力的技术对则责任进行理解和划分。

但在更下层,问题被隐蔽,有时难以有明确的责任划分。
此时最佳方式就是鼓励多交流。

8《正交性》

“正交性”是几何学术语。如果两条直线相交成直角,他们就是正交的。
它的特点是:两条轴上的值他们之间不互相依赖:你改变X值的时候,Y值不受影响。

在软件中,该术语表示两个或多个事物之间不相依赖或者说解耦性
例如:

  • 数据库代码和用户界面是正交的:你可以改动界面逻辑而不影响数据库逻辑;也可以改动数据库逻辑而不影响界面。

换言之——
消除无关事物之间的影响

正交性与DRY紧密相关。拥有多种好处,例如:

  • 提高生产率
  • 降低风险
  • 项目团队更好的职责划分
  • 更有利于测试

编写代码时有若干技术维护正交性,例如:

  • 设计独立、良好定义的组件
  • 让你的代码保持解耦
  • 避免使用全局数据
  • 避免编写相似的函数

9《可撤销性》

出于多种原因,一个决定很可能会在未来被改变。
为了让此造成的损失最小,需要让自己的劳动具备“可撤销性”。

换言之,就是更具有灵活性

  • 小到底层代码具有灵活性
  • 大到整体架构具有灵活性

10《曳光弹》

在黑暗中用机枪射击时,怎样知道正确的射击角度?
有两种选择:

  1. 掌握所有的情况,例如:子弹射击速度,重力,气压,风向等等等,最终精确计算出正确的射击角度。
  2. 使用曳光弹!它具有和常规子弹相同的弹道,而且会发光。这样,你可以及时根据曳光弹的弹道来调整,最终得到正确的射击角度。

软件开发也是一样,当接触一个新项目时:
有两种选择:

  1. 你可以准确地划分模块,然后每个模块在真空中测试。等到所有模块都制作完毕,再将他们合并在一块看效果。
  2. 你也可以像“曳光弹”一样:先构建一个能直达核心功能的代码,明确轨迹。然后再一步步往上面添加需要的功能。

使用曳光弹有很多好处:

  • 用户能够及早看到工作的东西
  • 开发者构建了一个他们能在其中工作的结构
  • 你有了一个集成的平台
  • 你有了可用于演示的东西
  • 你将更能感受到工作进展

不过,曳光弹并非总能击中目标。
如果失败了,你可以进行调整,而花费的代价会相对较少。

“曳光弹”与“原型制作”有区别:

  • 原型用后即扔,但是曳光弹会成为骨架的一部分。
  • 原型是在曳光弹之前的情报搜集工作。

11《原型与便笺》

许多不同的行业都使用原型实验来验证具体的想法,例如:

  • 制作粘土模型用于风洞测试。

软件工程也是一样,使用原型是为了分析和揭示风险,降低修正的代价。

原型应该研究什么样的问题?

  • 有风险的
  • 没有试过的
  • 关键性的
  • 未被证明的
  • 实验性的
  • 有疑问的

具体来说:

  • 架构
  • 已有系统的新功能
  • 外部数据的结构或内容
  • 第三方工具或组件
  • 性能问题
  • 用户界面设计

构建原型时忽略哪些细节?

  • 正确性
  • 完整性
  • 健壮性
  • 风格

架构原型要考虑的问题:

  • 责任是否得到了良好的定义
  • 协作是否得到了良好的定义
  • 耦合是否得以最小化
  • 你能否确定潜在的重复
  • 接口定义和各项约束是否可以接受
  • 模块是否能在需要时访问到数据

如果发现自己处于不能放弃细节的环境中,就要问自己,是否真的在构建原型,是不是应该构建“曳光弹”?

12《领域语言》

虽然,计算机语言应该是抽象的。
但是,计算机语言会影响你思考具体问题的方式。

每种语言都有自己的特性,例如:静态或动态,单继承或多继承。
这样的特性将会为你提示或者隐藏特定的解决方案。

相反,领域专门的语言,将提示出方案。

实现这样的小语言的方式:

  • 写解析器
  • 扩展已有的语言,比如Python。

这样的语言有两种方式使用:

  • 数据语言。(通常表示配置)
  • 命令语言。(表示流程)

按照与主应用的关系,可以分为:

  • 独立的
  • 嵌入主应用的

另外,实现这样的小语言也是有成本的,你需要进行权衡:

  • 容易开发的语言,可能不容易理解和使用。
  • 难开发的语言,可能使用起来容易。

13《估算》

通过学习估算,你可以对事物的数量级有直觉,快速确定一个方案的可行性。

在某种程度上,所有的解答都是估算,因此关键是:解答的语境是什么?

另一件有趣的事情是,使用的单位会对结果的解读造成影响。

估算的流程:

  1. 理解提问内容
  2. 建立系统的模型
  3. 把模型分解为组件
  4. 给每个参数指定值
  5. 计算答案

最后,追踪自己的估算能力。

猜你喜欢

转载自blog.csdn.net/u013412391/article/details/114873621