掘金 阅读 ( ) • 2021-06-23 17:51
.markdown-body{word-break:break-word;line-height:1.75;font-weight:400;font-size:15px;overflow-x:hidden;color:#333}.markdown-body h1,.markdown-body h2,.markdown-body h3,.markdown-body h4,.markdown-body h5,.markdown-body h6{line-height:1.5;margin-top:35px;margin-bottom:10px;padding-bottom:5px}.markdown-body h1{font-size:30px;margin-bottom:5px}.markdown-body h2{padding-bottom:12px;font-size:24px;border-bottom:1px solid #ececec}.markdown-body h3{font-size:18px;padding-bottom:0}.markdown-body h4{font-size:16px}.markdown-body h5{font-size:15px}.markdown-body h6{margin-top:5px}.markdown-body p{line-height:inherit;margin-top:22px;margin-bottom:22px}.markdown-body img{max-width:100%}.markdown-body hr{border:none;border-top:1px solid #ddd;margin-top:32px;margin-bottom:32px}.markdown-body code{word-break:break-word;border-radius:2px;overflow-x:auto;background-color:#fff5f5;color:#ff502c;font-size:.87em;padding:.065em .4em}.markdown-body code,.markdown-body pre{font-family:Menlo,Monaco,Consolas,Courier New,monospace}.markdown-body pre{overflow:auto;position:relative;line-height:1.75}.markdown-body pre>code{font-size:12px;padding:15px 12px;margin:0;word-break:normal;display:block;overflow-x:auto;color:#333;background:#f8f8f8}.markdown-body a{text-decoration:none;color:#0269c8;border-bottom:1px solid #d1e9ff}.markdown-body a:active,.markdown-body a:hover{color:#275b8c}.markdown-body table{display:inline-block!important;font-size:12px;width:auto;max-width:100%;overflow:auto;border:1px solid #f6f6f6}.markdown-body thead{background:#f6f6f6;color:#000;text-align:left}.markdown-body tr:nth-child(2n){background-color:#fcfcfc}.markdown-body td,.markdown-body th{padding:12px 7px;line-height:24px}.markdown-body td{min-width:120px}.markdown-body blockquote{color:#666;padding:1px 23px;margin:22px 0;border-left:4px solid #cbcbcb;background-color:#f8f8f8}.markdown-body blockquote:after{display:block;content:""}.markdown-body blockquote>p{margin:10px 0}.markdown-body ol,.markdown-body ul{padding-left:28px}.markdown-body ol li,.markdown-body ul li{margin-bottom:0;list-style:inherit}.markdown-body ol li .task-list-item,.markdown-body ul li .task-list-item{list-style:none}.markdown-body ol li .task-list-item ol,.markdown-body ol li .task-list-item ul,.markdown-body ul li .task-list-item ol,.markdown-body ul li .task-list-item ul{margin-top:0}.markdown-body ol ol,.markdown-body ol ul,.markdown-body ul ol,.markdown-body ul ul{margin-top:3px}.markdown-body ol li{padding-left:6px}.markdown-body .contains-task-list{padding-left:0}.markdown-body .task-list-item{list-style:none}@media (max-width:720px){.markdown-body h1{font-size:24px}.markdown-body h2{font-size:20px}.markdown-body h3{font-size:18px}}

这是我参与更文挑战的第17天,活动详情查看: 更文挑战

假设一切都将运行良好

我们总是会假设: 一切都将运行良好, 每一项任务仅花费它所"应该"花费的时间

这里要求我们在做项目排期时, 要尽可能的考虑到所有的情况, 不要盲目自信, 也不要畏首畏尾, 要做到自信和迟疑相平衡, 在这里也可能会出现设计缺陷, 过早设计和过早优化. 但是是这种情况是所有项目不可避免的, 我们能做到的就是从全局出发, 统筹安排.

从全局出发

  1. 评估项目中所有会设计的点
  2. 确定项目的规划, 预期和目标
  3. 确定项目的开发规范, 文档的维护, 代理的管理
  4. 确定项目中的重要的时间节点, 也就是Milestone
  5. 确定参与项目的部门, 人员
  6. 罗列项目中有可能会遇到的问题, 如将要用到的新框架, 之前没有写过的新功能

深入局部之内

  1. 严格的细分功能模块, 及模块间的通信原则与方式
  2. 确定各个模块的人员, 及各个模块完成的时间结点
  3. 确定各个模块的工期安排
  4. 明确各个模块的完成的时间结点, 确定它们的主要顺序, 依赖顺序

最后根据全局分析和局部分析的结果, 来确定我们整个项目的安排.

人月神话

用人月作为衡量一项工作的规模是一个危险和带有欺骗性的神话. 错误的将进度与工作量相互混淆, 好比人员的数量和时间可以互换. 成本会随着开发产品的人数和时间的不同, 有着很大的变化, 进度却不是如此. 我们总是将人和工作量进行等价划分, 认为1个人做10天可以完成的项目, 10个人做1天就可以完成. 当意识到进度的偏移时, 下意识的反应是增加人力. 犹如用汽油灭火一样. 向进度落后的项目中增加人手, 只会使进度更加落后. 但是我们可能没有仔细思考过工作可能是不可切割的. 当向当前项目中增加人手时, 我们可能会遇到以下问题:

  1. 增加人员的培训成本
  2. 模块之间的耦合度很高, 不易拆分
  3. 人员之间的沟通成本增加
  4. 代码的质量参差不齐

因此, 在一个进程已经落后的软件项目中增加人手, 只会使它更落后.

对项目进行进行实时监督

由于对自己的估算缺乏信心, 我们通常不会有耐心持续地估算这项工作, 因此我们要持续的对项目进行估算. 对进度缺少跟踪和监督. 在每个项目中项目排期, 都是一个很让人头疼的问题. 那么我们如何更好的去进行项目的评估呢

  1. 严格的模块划分, 尽量减少模块间耦合

  2. 要持续不断的坚持项目的排期, 在每次的排期和项目结束后, 吸取经验和教训, 以对之后的项目评估有更好的安排

  3. 每次项目完成之后都要进行项目总结

    ​a. 项目是否如期完成, 是什么原因导致的项目延期

    ​b. 项目中遇到的问题, 以及为什么会出现这些问题, 在之后的开发中, 我们能否避免

    ​c. 在当前的排期中, 是否有不可控因素

    ​d. 是否有需求不明确导致, 或者有更紧急的任务要处理

    ​e. 是否我们缺少对项目进度的跟踪与监督

如何管理好一个工程项目?

在进行项目评估时, 我们要时刻去思考这些问题?

  1. 是否有清晰的目标?
  2. 是否有充足的人力?
  3. 是否有充足的材料?
  4. 是否有足够的时间?
  5. 是否有足够的技术?
  6. 是否有充分且透彻的沟通?
  7. 是否通过沟通进行了有条不紊的组织?

不变是愿望, 变化才是永恒 普遍的做法是, 选择一种方法, 试试看; 如果失败了, 没关系, 再试试别的方法. 不管怎么样, 重要的是先去尝试.

软件维护

当我们进行软件的维护时, 要认识到软件维护的本是对设计缺陷的修复

对于一个程序, 其维护总成本通常是开发成本的40%或者更多. 该成本受用户数目的影响很大. 用户越多, 所发现的错误也就越多. 上一个版本中被发现和修复的bug, 在新的版本中仍会出现. 新版本中的新功能会产生新的bug. 解决了这些问题以后, 程序会正常运行几个月, 接着错误率会重新攀升. 是因为用户对软件的使用达到了新的熟练水平, 他们开始运用新的功能.

程序维护中的一个基本问题 - 缺陷修复总会以固定的几率(20%~50%)引入新的bug. 前进两步, 后退一步. 为什么bug不能彻底的被修复? 看上去很微小的错误, 似乎仅仅是局部操作上的失败, 实际上却是系统级别的问题. "事物在最初总是最好的"

写给自己: 不要当一个斐波那契程序员, 每天都在改昨天和前天的bug. 在我的感觉中改bug可能比写功能更需要我们去分析和思考. 也更值得我们去探索和改进, 可能也是我们水平提高的一种很重要的方式与方法.

软件开发与软件维护

系统软件开发是减少混乱度的过程, 所以本身处于亚稳定的状态.

软件维护是提高混乱度的过程, 即使是最熟练的软件维护工作, 也只是放缓了系统退化到非稳定状态的进程.

自上而下的设计

清晰的结构和表达方式更容易对需求和模块功能进行精确的描述 模块分割和模块独立性避免了系统级的bug 细节的控制使结构上的缺陷更加容易识别 设计在每个精华步骤上都是可以测试的, 所以测试可以尽早开始, 并且每个步骤的重点可以放在合适的级别上

如何保证一个大型项目的进度?

制定一个严格的进度表, 该进度表由里程碑和日期组成 里程碑必须是具体的, 特定的和可度量的事件, 能进行清晰的定义 每个小阶段的延期, 最后就会造成整个项目进度的大的延迟 一天一天的进度落后比起重大灾难更难以识别, 更不容易防范和更加难以弥补我们一直都知道的是: 千里之行, 始于足下, 万里之堤, 溃于蚁穴. 可是在实际的工作生活中, 我们总是大大咧咧, 对于小事情毫不在意, 尤其在模块间耦合度较高的情况下, 可能牵一发而动全身. 因此当我们制定好计划后, 一定要有严格的执行标准, 保证排期的顺利进行.

人月一直是个神话

人月之所以不能成为现实, 是因为增加人手的同时也增加了人与人之间的沟通成本. 增加了新人的培训成本, 而不是简单的1 + 1 >= 2的结果.