《代码大全》读书笔记一
摘自《Code Complete》一书,将书中的一些Check List和Key Points列出来,以备遗忘。
第一章 欢迎进入软件构建的世界 (Welcome to Softeware Construction)
key Points:
- 软件构建是软件开发的核心活动:构建活动是每个项目中唯一一项必不可少的工作。
- 软件构建的主要活动包括:详细设计、编码、调试、集成、开发者测试(包括单元测试和集成测试)。
- 构建也常被称作“编码”和“编程”。
- 构建活动的质量对软件的质量有着实质性的影响。
- 最后,你对“如何进行构建”的理解程度,决定了你这名程序员的优秀程度。
第二章 用隐喻来更充分地理解软件开发 (Metaphors for a Richer Understanding of Softeware Development)
Key Points:
- 隐喻是启示而不是算法。因此它们往往有一点随意。
- 隐喻把软件开发过程与其他你熟悉的活动联系在一起,帮助你更好地理解。
- 有些隐喻比其他一些隐喻更贴切。
- 通过把软件的构建过程比作是房屋的建设过程,我们可以发现,仔细的准备是必要的,而大型项目和小型项目之间也是有差异的。
- 通过把软件开发的实践比作是智慧工具箱的工具,我们又发现,每位程序员都有许多工具,但并不存在任何一个能适合所有工作的工具,因地制宜地选择正确工具是成为能有效编程的程序员的关键。
- 不同的隐喻彼此并不排斥,应当使用对你最有益处的某种隐喻组合。
第三章 三思而后行:前期准备 (Measure Twice, Cut Once: Upstream Prerequisites)
Checklist: 需求 (Requirements)
这张需求核对表包含了一系列的问题——问问自己项目的需求工作做得如何。本书并不会告诉你如何做好需求分析,所以列表里面也不会有这样的问题。在开始构建之前,用这份列表做一次“心智健全”检查,看看你的地基到底有多坚固——用“需求里氏震级”来衡量。
并不是需求表中所有的问题都使用于你的项目。如果你做的是一个非正式项目,那么你会发现有些东西根本就不需要考虑。你还会发现一些问题你需要考虑,但不需要做出正式回答。如果你在做一个大型的、正式的项目,你也许就要逐条考虑了。
针对功能需求
- 是否详细定义了系统的全部输入,包括其其来源、精度、取值范围、出现频率等?
- 是否详细定义了系统的全部输出,包括目的地、精度、取值范围、出现频率、格式等?
- 是否详细定义了所有输出格式(Web页面、报表、等等)?
- 是否详细定义了所有硬件及软件的外部接口?
- 是否详细定义了全部外部通信接口,包括握手协议、纠错协议、通信协议等?
- 是否列出了用户想要做的全部事情?
- 是否详细定义了每个任务所用的数据,以及每个任务得到的数据?
针对非功能需求(质量需求)
- 是否为全部必要的操作,从用户的视角,详细描述了期望响应时间?
- 是否详细描述了其他与计时有关的考虑,例如处理时间、数据传输率、系统吞吐量?
- 是否详细定义了安全级别?
- 是否详细定义了可靠性,包括软件失灵的后果、发生故障时需要保护的至关重要的信息、错误检测与恢复的策略等?
- 是否详细定义了机器内存和剩余磁盘空间的最小值?
- 是否详细定义了系统的可维护性,包括适应特定功能的变更、操作环境的变更、与其他软件的接口的变更能力?
- 是否包含对“成功”的定义?“失败”的定义呢?
需求的质量
- 需求是用用户的语言书写的吗?用户也这么认为吗?
- 每条需求都不与其他需求冲突吗?
- 是否详细定义了相互竞争的特性之间的权衡——例如,健壮型与正确性之间的权衡?
- 是否避免在需求中规定设计(方案)?
- 需求是否在详细程度上保持相当一致的水平?有些需求应该更详细地描述吗?有些需求应该更粗略地描述吗?
- 需求是否足够清晰,即使转交给一个独立的小组去构建,他们也能理解吗?开发者也这么想吗?
- 每个条款都与待解决的问题及其解决方案相关吗?能从每个条款上溯到它在问题域中对应的根源吗?
- 是否每条需求都是可测试的?是否可能进行独力的测试,以检查满不满足各项需求?
- 是否详细描述了所有可能的对需求的改动,包括各项改动的可能性?
需求的完备性
- 对于在开始开发之前无法获得的信息,是否详细描述了信息不完全的区域?
- 需求的完备性是否能达到这种程度:如果产品满足所有需求,那么它就是可接受的?
- 你对全部需求都感到舒服吗?你是否已经去掉了那些不可能实现的需求——那些只为了安抚客户和老板的东西?
Checklist: 架构 (Architecture)
以下是一份问题列表,优秀的架构应该关注这些问题。这张核对表的意图并非用做一份有关如何做架构的完全指南,而是作为一种实用的评估手段,用来评估软件食物链到了程序员这一头还有多少营养成分。这张核对表可用做你自己的核对表的出发点。就像“需求”的核对表一样,如果你从事的是非正式项目,那么你会发现其中某些条款甚至都不用去想。如果你从事的是更大型的项目,那么大多数条款都会是很有用的。
针对各架构主题:
- 程序的整体组织结构是否清晰?是否包含一个良好的架构全局观(及其理由)?
- 是否明确定义了主要的构造块(包括每个构造块的职责范围及与其他构造块的接口)?
- 是否明显涵盖了“需求”中列出的所有功能(每个功能对应的构造块不太多也不太少)?
- 是否描述并论证了那些最关键的类?
- 是否描述并论证了数据设计?
- 是否描述定义了数据库的组织结构和内容?
- 是否指出了所用的关键的业务规则,并描述了其对系统的影响?
- 是否描述了用户界面设计的策略?
- 是否将用户界面模块化,使界面的变更不会影响程序其余部分?
- 是否描述并论证了处理I/O的策略?
- 是否估算了稀缺资源(如线程、数据库连接、句柄、网络带宽等)的使用量,是否描述并论证了资源管理的策略?
- 是否描述了架构的安全需求?
- 架构是否为每个类、每个子系统、或每个功能域(functionality area)提出空间与时间预算?
- 架构是否描述了如何达到可伸缩性?
- 架构是否关注互操作性?
- 是否描述了国际化/本地化的策略?
- 是否提供了一套内聚的错误处理策略?
- 是否规定了容错的办法(如果需要)?
- 是否证实了系统各个部分的技术可行性?
- 是否描述了过度工程的方法?
- 是否包含了必要的“买 vs. 卖”的决策?
- 架构是否描述了如何加工被复用的代码,使之符合其他架构目标?
- 是否将架构设计得能够适应很可能出现的变更?
架构的总体质量
- 架构是否解决了全部需求?
- 有没有哪个部分是“过度架构/overarchitected“或“欠架构/underarchitected”?是否明确宣布了在这方面的预期指标?
- 整体架构是否在概念上协调一致?
- 顶层设计是否独立于用作实现它的机器和语言?
- 是否说明了所有主要的决策和动机?
- 你,作为一名实现该系统的程序员,是否对这个架构感觉良好?
Key Points:
- 构建活动的准备工作的根本目标在于降低风险。要确认你的准备活动是在降低风险,而非增加风险。
- 如果你想开发高质量的软件,软件开发过程必须由始至终关注质量。在项目初期关注质量,对产品质量的正面影响比在项目末期关注质量的影响要大。
- 程序员的一部分工作是教育老板和合作者,告诉他们软件开发过程,包括在开始编程之前进行充分准备的重要性。
- 你所从事的软件项目的类型对构建活动的前期准备有重大影响——许多项目应该是高度迭代式的,某些应该是序列式的。
- 如果没有明确的问题定义,那么你可能会在构建期间解决错误的问题。
- 如果没有做完良好的需求分析工作,你可能没能察觉待解决问题的重要细节。如果需求变更发生在构建之后的阶段,其代价是“在项目早期更改需求”的20至100倍。因此在开始编程之前,你要确认“需求”已经到位了。
- 如果没有做完良好的架构设计,你可能会在构建期间用错误的方法解决正确的问题。架构变更的代价随着“为错误的架构编写的代码数量”增加而增加,因此,也要确认“架构”已经到位了。
- 理解项目的前期准备所采用的方法,并相应地选择构建方法。