测试驱动的开发是否迫使我遵循SOLID?


15

我从TDD的实践者那里听到很多东西,TDD的优势之一是它迫使开发人员遵循SOLID原则(单一职责,开放式封闭,Liskov替代,接口隔离和依赖倒置)。但是对我而言,只需编写一些测试(主要是单元测试)就足以理解遵循SOLID(从而创建可测试的体系结构)非常重要。

TDD是否会迫使开发人员更积极地遵循SOLID,而不仅仅是编写单元测试?


1
TDD主要是关于强迫开发人员编写测试。因此,如果您说编写单元测试使您能够编写SOLID代码,那么我猜这是说TDD迫使您编写SOLID代码。不过,这只是基于您所说的内容,并不能准确反映我的意见,您可以在我的回答中看到。
Yam Marcovic

1
Yam:我不同意,TDD与编写单元测试无关。TDD即将为当前的问题提供最小的复杂且正确的解决方案。测试只是该程序的副产品
Amit Wadhwa

根据定义,TDD是关于在代码之前编写测试的。从理论上讲,即使没有测试,您也可以创建一个最小复杂的解决方案。这些测试只是为您提供即时反馈和回归意识。由于仍然可以使用测试创建过于复杂的解决方案,因此TDD本身并不是要创建最小复杂的解决方案。这与您所说的相反。优雅的解决方案是该过程的副产品,而不是相反。
Yam Marcovic

Answers:


24

首先,TDD并不严格强迫你写可靠的代码。如果愿意,您可以执行TDD并创建一个大混乱。

当然,了解SOLID原理会有所帮助,因为否则您可能最终对许多问题都没有一个好的答案,因此编写了不好的代码并伴随着不好的测试。

如果您已经了解SOLID原则,TDD会鼓励您考虑并积极使用它们。

就是说,它并不一定涵盖SOLID中的所有字母,但强烈鼓励并促进您至少部分地编写SOLID代码,因为这样做会使后果立即可见并令人讨厌。

例如:

  1. 您需要编写解耦的代码,以便可以模拟所需的内容。这支持了依赖倒置原则
  2. 您需要编写清晰明了且简短的测试,这样您就不必在测试中进行太多更改(否则可能会成为大量的代码噪声源)。这支持单一责任原则
  3. 这可能会引起争议,但是接口隔离原则允许类依赖较轻的接口,这些接口使模拟更易于理解和理解,因为您不必问“为什么还不对这5种方法进行模拟?”,或者更重要的是,在决定模拟哪种方法时,您没有太多选择。如果您真的不想在测试之前遍历类的整个代码,而只是使用试错法来对它的工作原理有一个基本的了解,那么这很好。

遵循“打开/关闭”原则可能会很好地帮助在代码编写的测试,因为它通常使您可以覆盖从被测类派生的测试类中的外部服务调用。在TDD中,我认为这不是其他原则所必需的,但我可能会误解。

如果您想最小化类的更改以接收不支持的实例,而该实例恰好实现了相同的静态类型的接口,那么遵循Liskov替换规则将非常有用,但是在适当的测试用例中这不太可能发生,因为通常不会通过任何测试中的类依赖项的真实世界实现。

最重要的是,制定SOLID原则是为了鼓励您编写更简洁,更易理解和可维护的代码,TDD也是如此。因此,如果您正确执行TDD,并且注意代码和测试的外观(并且并不难,因为您会立即获得反馈,API和正确性),那么通常您就不必担心SOLID原则。


另外,除非您遵循“打开/关闭”和“ Liskov”替换,否则您的模拟游戏将在以后中断。因此,即使TDD可能无法帮助您强制执行OCP和LSP,创建的测试也会在中断时通知您。测试效果一般,但仍然值得一提。
乔纳斯·舒伯特·厄兰森

9

没有

由于可以持续进行重构,因此TDD可以使遵循良好做法更容易,但是它并不强迫您遵循任何原则。它所做的只是确保您编写的代码已经过测试。您可以在编写满足测试要求的代码时遵循自己喜欢的任何原则。或根本没有原则。


2

当我开始进行TDD时,我对SOLID原则的理解增加了一个数量级。当我开始考虑如何模拟依赖关系时,我几乎意识到代码库中的每个组件都有潜在的替代实现。测试一个简单的公共API有多容易。

它还提供了对大多数设计模式的更深入的了解。尤其是策略模式。


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.