我现在正在对一年中写的应用程序进行单元测试,然后才开始努力进行单元测试.我意识到我写的类很难进行单元测试,原因如下:
总的来说,设计似乎没有任何问题,只是它太紧密耦合(这本身就是一件坏事).我想如果我已经为每个类编写了自动化测试用例,因此确保我没有堆积额外的依赖关系或耦合使该类工作,该类可能更好地设计.
这个理由是否有水?你有什么经历?
Pét*_*rök 13
是的,你是对的.一个不能单元测试难以进行单元测试的类(几乎总是)没有很好的设计(有例外,一如既往,但这些很少见 - 恕我直言,最好不要试图以这种方式解释问题).缺乏单元测试意味着它更难维护 - 无论何时修改其中的任何内容,您都无法知道是否已破坏现有功能.
而且,如果它与程序的其余部分(共同)相关,那么它的任何变化都可能会破坏甚至代码中看似无关的,相距甚远的部分.
TDD不仅仅是一种测试代码的方式 - 它也是一种不同的设计方式.从一开始就有效地使用 - 并考虑使用 - 您自己的类和接口可能会导致与传统的"代码和祈祷"方式截然不同的设计.一个具体的结果是,通常大多数关键代码都与系统的边界隔离,即存在包装/适配器以隐藏例如系统其余部分的具体DB,以及"有趣"(即可测试)代码不在这些包装器中 - 这些包装尽可能简单 - 但在系统的其余部分.
现在,如果你有一堆没有单元测试的代码并希望覆盖它,那么你就有了挑战.模拟框架可能会有很大的帮助,但是为这样的代码编写单元测试仍然很麻烦.处理此类问题的技术(通常称为遗留代码)的一个很好的技术来源是Michael Feathers的"有效地使用遗留代码".
Ale*_*lli 11
我发现依赖注入是最有助于使我的代码可测试的设计模式(并且通常也可以重用并适用于与我为其设计的原始内容不同的上下文).我的Java同事喜欢Guice ; 我主要用Python编程,所以我通常会"手动"进行依赖注入,因为鸭子打字很容易; 但它是静态或动态语言的正确基础DP(不要让我开始"猴子修补"......让我们说它不是我的最爱;-).
一旦你的类准备好"从外部"接受它的依赖,而不是让它们硬编码,你当然可以使用假的或模拟版本的依赖项来使测试更容易和更快地运行 - 但这也打开了其他可能性.例如,如果当前设计的类的状态很复杂且难以设置,请考虑状态设计模式:您可以重构设计,以便状态存在于单独的依赖项中(您可以根据需要设置和注入)并且类本身主要负责行为(更新状态).
当然,通过这种方式进行重构,您将引入越来越多的接口(抽象类,如果您使用的是C++) - 但这完全可以:它是一个很好的原则,"编程到接口,而不是实施".
所以,为了直接解决你的问题,你是对的:测试的难度绝对是极端编程称之为"代码味道"的设计等价物.然而,从好的方面来说,有一个非常明确的途径来重构这个问题 - 你不必拥有一个完美的设计(幸运的是! - ),但可以随时增强它.我建议将Refactoring to Patterns这本书作为这个目的的良好指导.
| 归档时间: |
|
| 查看次数: |
764 次 |
| 最近记录: |