2天时间,聊今年最热的 Agent、上下文工程、AI 产品创新等话题。2025 年最后一场~ 了解详情
写点什么

测试驱动开发与遗留代码的问题

  • 2009-11-21
  • 本文字数:1633 字

    阅读完需:约 5 分钟

Allan Baljeu 试图在他庞大的、C++ 遗留代码库中使用 TDD,结果遇到了很大的麻烦,因为:

我们后来得到的类不能完全实现希望其具备的功能,当有人使用这些类时,会想要得到更加完整的实现,然而却会发现原有的设计不够完善,要进行新的设计,有些期望(测试)要做出改变,而之前对这些类的使用也得调整。

他在思考前期大规模设计(BDUF)也许有助于解决这个问题。 George Dinwiddie 敏捷教练,他认为Alan 的设计是在试图告诉他些什么。人们必须要注意“干净代码(clean code)”的基本原则,要注意基本的内聚和耦合性方面的问题(比如 SOLID 原则)。

Mike “Geepaw” Hill 也是 Agile Coach ,他提到:在他指导敏捷团队的这些年来,下列原因之一可能是类似问题的根本原因:

  • 团队在重构方面做得不够,因此你的类没有做到最小化。
  • 团队在“尽量简单”方面的技能还不够,同样如此。
  • 团队还没有采取具备侵略性和快速度的微测试(microtesting,也就是 **单元测试),所以改变常常会破坏测试 **
  • 团队不知道如何处理跨团队、或是公司对公众之间的依赖,比如公布 API 的情况
  • 团队既没有结对,也没有在开放空间中工作,这极大降低了团队层面的知识理解和传递
  • 团队似乎没有具备快速构建的能力
  • 团队可能还在使用老古董级别的工具

Keith Ray 极限编程教练,他提出:有了遗留代码(也就是欠下很高技术债的系统),实现一个故事的成本完全取决于偿还技术债的成本。接下来,他提出一种解决方式:

要让代码的结构更好(偿还技术债务),不管什么时候,当你需要集成一个新功能时,你应该同时注意新旧代码中的异味,并在发现异味时,马上重构,消除异味。 你可以手工采取小而安全的步骤进行重构(即使使用 C++)。要紧跟 Martin Fowler《重构》一书中的步骤,除非你能做到得心应手。带有 gcc 的 Eclipse 有些重构功能可以使用:“抽取方法”和“重命名”。“重命名”能够知道命名所在的范围,所以要比查找和替换更为安全。“抽取方法”和其他的重构功能可能有 bug,使用它们的时候要小心。像改变函数签名这样的东西,“依靠编译器”能够展示出哪里需要改变。

你还需要测试来保证没有破坏现有功能。Michael Feather 的《修改代码的艺术》提供了很多向遗留代码中加入测试的技巧。从更高层面来看,代码异味是破坏优秀设计原则的表现。举例而言:单一职责原则(SRP)认为:每个类、方法、模块只应该有一个意图。还有些原则是与耦合、内聚和管理依赖关系相关的。相比使用这些抽象原则,发现代码异味常常更为容易。“大类”和“大方法”可以通过“抽取类”和“抽取方法 / 移动方法”修改,不过知道 SRP 有助于判断抽取类或方法的哪一部分。

也许“告知,不要询问”是最重要的设计原则:不要分离功能和数据……恶劣的代码常常把功能实现放在一个地方,从其他地方得到需要的数据,这就造成了依赖性方面的问题,同时代码缺少局部性(locality)。其症状就是:“添加一个新功能,要修改多处代码。”代码异味“散弹枪式手术”、“依恋情结”、“参数列表过长”都是这样造成的。

尽快得到反馈能带来更多重构,这最终将会加快新功能的开发。尝试进行并行构建(分布式编译),尝试让源代码文件和头文件更小,降低头文件的复杂度——可使用前向声明、避免内联代码、尝试让每个类只有一个头文件 / 源代码文件。大量使用“指向实现的指针(pimpl idiom)”能降低 10% 的编译时间,但是也可能把“大类”和“依恋情结”这样的代码异味给隐蔽起来。

重构要比重写更好,其优势在于:你总是有可工作的代码。如果你的手工和自动化测试都很好,那你就可以交付代码了,即使目前的状态处于“优秀设计”和“恶劣设计”之间。

Keith 还写了“ Refactoring: Small Steps Guaranteed to Help You Clean Up Your Code ”,该文章发表于 Better Software Magazine,讲述如何重构 C++ 代码。

InfoQ 之前的相关内容:《如何处理遗留代码》《Bob 大叔谈测试驱动开发的适用性》《如何坚持TDD:使用者出现的问题以及解决方案》

查看英文原文: Test Driven Development and the Trouble with Legacy Code

2009-11-21 05:312252
用户头像

发布了 479 篇内容, 共 181.0 次阅读, 收获喜欢 53 次。

关注

评论

发布
暂无评论
发现更多内容

Java 18开发者新特性详解:简易Web服务器、代码片段标注与UTF-8默认编码

qife122

Java 新特性

高效训练大规模图神经网络的创新方法

qife122

图神经网络 GPU加速

✨ 梦精灵AI 2.0 应用大更新!管理中心+浏览器插件双升级,这些功能太香了!

龙正哲

提示词 提示词管理

javax.security.auth.login.LoginException: Receive timed out

刘大猫

人工智能 数据挖掘 算法 数据分析 LoginException

Gemma 3:单GPU/TPU可运行的最强开源模型

qife122

开源技术 AI模型

基于YOLOv8的矿井内煤炭图像智能识别|完整源码数据集+PyQt5界面+完整训练流程+开箱即用!

申公豹

人工智能

释放美杜莎:快速可扩展的智能合约模糊测试技术

qife122

区块链 开源

配电 二次控制回路经验总结(2)

万里无云万里天

工业 工厂运维

配电 二次控制回路经验总结(3)

万里无云万里天

工业 工厂运维

AI编程实战|提示词工程-N-Shot学习与实践

Jxin

编程 AI 提示词 AI辅助编程

NotebookLM替代工具技术解析

qife122

AI工具 技术对比

配电 二次控制回路经验总结(1)

万里无云万里天

工业 工厂运维

一个普通文科生的AI创业之路丨2023-2025

阿星AI工作室

创业 AI 产品经理 经验之谈 超级个体

基于跨话语重评分的包容性语音识别技术

qife122

语音识别 图神经网络

某中心发布云端浏览器工具AgentCore,赋能AI网页交互

qife122

人工智能 云计算

多租户模型推理成本追踪方案解析

qife122

人工智能 成本优化

配电 低压电工经验总结(8)

万里无云万里天

工业 工厂运维

配电 低压电工经验总结(9)

万里无云万里天

工业 工厂运维

AI 编程实战|提示词工程-COT&TOT学习与实践

Jxin

编程 AI 提示词 提示词工程 AI辅助编程

AI 编程实战|提示词工程-Reflexion反思机制学习与实践

Jxin

编程 AI 提示词 提示词工程 AI辅助编程

spaCy v2.3发布:新增5种语言模型与性能优化

qife122

自然语言处理 开源工具

从App Store高效获取iOS渗透测试所需的.ipa文件

qife122

ios安全 逆向工程

微软漏洞赏金计划丰收季:六大安全研究员获嘉奖

qife122

漏洞赏金 IE11漏洞

微软强化Windows 11防御文件链接攻击

qife122

Windows安全 权限提升

认证实验室实战演练 - 深入解析认证与授权漏洞

qife122

网络安全 渗透测试

配电 高压电工经验总结(1)

万里无云万里天

工业 工厂运维

合规部署大语言模型:AI编排与可解释性

qife122

金融服务 合规

Mac下Elasticsearch7.x安装及Springboot集成

程序员架构进阶

elasticsearch #架构 8月月更 检索引擎 RAG 框架

配电 低压电工经验总结(10)

万里无云万里天

工业 工厂运维

如何安全使用localStorage保护敏感数据

qife122

数据加密 前端安全

PTI中的SMEP模拟技术解析

qife122

内核安全 SMEP

测试驱动开发与遗留代码的问题_研发效能_Mark Levison_InfoQ精选文章