类别: 原则
类型: 软件开发原则
起源: 极限编程,1999 / 重构,1999
别名: YAGNI、你不会需要它、你不会需要它
类型: 软件开发原则
起源: 极限编程,1999 / 重构,1999
别名: YAGNI、你不会需要它、你不会需要它
快速回答 — YAGNI 原则(You Aren’t Gonna Need It)是一个软件开发指南,建议程序员不要在实际需要之前添加功能。YAGNI在1990年代后期由极限编程(XP)从业者推广,作为应对常见趋势的对策:预测未来需求并”以防万一”构建复杂的系统。该原则认为,过早的泛化会增加复杂性,消耗开发时间,而且当实际需求与预测不符时,这些努力往往会被浪费。
什么是 YAGNI 原则?
YAGNI 原则是一种设计准则,劝告不要在代码库或用户群明确需要之前实现功能或构建系统。YAGNI是”You Aren’t Gonna Need It”(你不会需要它)的首字母缩写(有时是”You Aren’t Going to Need It”),捕捉到了该原则的核心信息:抵制为假设的未来场景构建灵活性的诱惑。“总是在真正需要时实现事物,而不是在你仅仅预见可能需要它们时。” — 肯特·贝克,《极限编程解析》该原则源于极限编程(XP)方法论,该方法论强调简单性、反馈和勇气作为核心价值。XP从业者观察到,开发者经常花费大量时间构建”灵活”的系统来预测各种未来场景——这些场景往往永远不会出现。当这些未来需求确实出现时,它们通常与预测足够不同,以至于准备工作仍然是浪费。 YAGNI与”技术债务”概念密切相关。在需要之前编写的每一行代码都是必须维护、理解和解错的债务。当实际需求出现时,匆忙的抽象可能不太合适,需要重构,这比简单地直接实现需要的功能花费更多时间。YAGNI主张更简单的道路:实现你现在需要的,当需求变得清晰时再重构。
YAGNI 原则的三层理解
- 入门: 当想要添加”防未来”代码时,停下来问:“我实际上会使用这个,还是只是在猜测?“如果是猜测,就跳过它。你总是在需要被证实后添加它。
- 实践: 使用测试驱动开发来揭示实际需求。让测试揭示真正需要什么功能,而不是预先想象所有可能的用例。
- 进阶: 平衡YAGNI与注意代码何时需要重构的”气味”。有时需要足够紧迫以证明准备工作是合理的——但区分真正的信号和投机性的预测。
起源
YAGNI 原则是在1990年代后期出现的极限编程(XP)方法论中阐述的。肯特·贝克(Kent)创造了这个术语并领导了XP运动,他将YAGNI描述为区别于传统软件开发方法论的核心实践之一。 该原则在马丁·福勒(Martin Fowler)有影响力的著作《重构》(1999年)中有重要讨论,该书讨论了YAGNI与重构过程的关系。福勒认为,当需求紧迫时,通过重构添加灵活性是适当的,但过早的泛化会导致不必要的复杂代码。 YAGNI流行的时机正值网络泡沫时代,软件项目经常面临快速交付的巨大压力。该原则为快速开发的混乱提供了一个务实的回应:抵制构建复杂系统的冲动,专注于满足当前需求,并相信未来需求可以在到来时得到解决。这种方法在许多项目中证明是有效的,导致YAGNI在XP社区之外被主流软件开发所采用。核心要点
应用场景
功能开发
只构建用户或利益相关者明确要求的功能。避免添加当前不有用的配置选项、钩子或扩展点。
API设计
根据当前需求设计API,而不是想象的未来用例。根据需求添加端点和参数,而不是预先猜测。
数据库模式
为当前需求创建数据库结构。随着应用程序的发展添加表、列和关系,而不是试图预测所有未来的需求。
框架选择
根据当前项目需求选择框架和库。当更简单的解决方案满足当前需求时,避免添加复杂的框架”以防万一”。
经典案例
Stripe,这家在线支付处理公司,在其早期开发中 famously 采用了YAGNI 原则。Stripe没有构建 elaborate 的欺诈检测系统、国际功能或高级分析工具来预测未来需求,而是专注于极其出色地做一件事:实现简单、可靠的在线支付。随着公司成长,需求变得清晰,他们逐步添加功能。这种方法使Stripe比那些花了数年构建综合平台的竞争对手移动得更快。当Stripe确实添加新功能时,它们是由实际客户需求驱动的,而不是投机性的未来需求,结果是产品更好地匹配市场需求。边界与失效场景
YAGNI 原则虽然有价值,但可能被误用。首先,有些需求是真正可预测的。构建支持预期规模或符合已知法规的基础设施可能证明”准备”是合理的,而不是投机性的。 其次,YAGNI并不意味着忽略好的设计实践。编写可重构的干净代码与构建投机性功能不同。该原则警告不要添加额外的功能,而不是不要保持代码质量。 第三,在某些领域,某种程度的超前思考是必不可少的。安全系统需要预测攻击向量;安全关键系统需要考虑故障模式。YAGNI在这些情况下应该深思熟虑地应用。常见误区
YAGNI意味着永远不提前计划
YAGNI意味着永远不提前计划
YAGNI不禁止考虑架构——它禁止构建不必要的功能。支持已知需求的好架构仍然是有价值的。
YAGNI意味着写糟糕的代码
YAGNI是关于功能范围,而不是代码质量。解决当前需求的干净、可维护的代码总是比不管YAGNI如何的混乱代码更好。
YAGNI与DRY冲突
DRY和YAGNI协同工作。DRY在重复存在时提取重复;YAGNI在重复被证实之前防止创建抽象。它们以不同的方式简化代码库。
相关概念
KISS原则
YAGNI和KISS都主张简单性。YAGNI防止添加不必要的功能;KISS防止使这些功能复杂化。
DRY原则
DRY在重复存在时提取重复;YAGNI防止创建不必要的重复。它们相互补充,保持简单的代码库。
最小可行产品
MVP通过只构建提供价值所需的功能来体现YAGNI。额外功能根据反馈添加。
技术债务
YAGNI通过防止不必要的代码来帮助避免累积技术债务。每个未使用的功能都会增加维护负担。
测试驱动开发
TDD自然支持YAGNI,因为它只驱动使测试通过所需的功能。