单元测试小技巧(2)

发表于:2015-07-31来源:uml.org.cn作者:不详点击数: 标签:单元测试
returns the sum of the two numbers Function Sum(ByVal a As Integer, ByVal b As Integer) As Integer 你可以向如下的方式写一个失败测试 TestMethod() _ Public Sub Sum_AddsOneAndTwo() Dim re

' returns the sum of the two numbers
Function Sum(ByVal a As Integer, ByVal b As Integer) As Integer

  你可以向如下的方式写一个失败测试

<TestMethod()> _
Public Sub Sum_AddsOneAndTwo()
Dim result As Integer = Sum(1, 2)
Assert.AreEqual(4, result, "bad sum");
End Sub

  初看上去这个处理像是一个写失败测试的好的方法,它完全错失了你写错误测试的初始点。

  一个失败测试验证了在代码中存在一些错误,当你的测试完成后这个测试应该是通过的,现在的例子中,无论如何,测试都将会失败,即使是代码完成,因为测试逻辑上不是正确的。如果希望测试通过测需要测试自身进行修改――而不是程序的代码的改变(当程序代码改变的时候,是test-first规划的意图)简短来说,这个测试不会反映出程序代码完成后的最终的结果,因此这个不是一个好的测试。

  TDD中一个好的测试要求你去修改代码,从而使它能够按照想要的方式工作,这一点要胜于强迫你去反映现在的真实情况或者一个非逻辑要求的渴望的结果。例如,当1+1返回0时就意味着测试失败。这个简单的例子和这种情况是相似的,在练习中,如果现在的需求是在工作的,测试应该可以反映你所期待的结果,然后你可以调整现在代码的情况去通过这个测试。

  作为一个规则,一个已经调通的测试不应该被移除掉,因为这个测试在维护工作中可以用于恢复测试。他们在你改变代码时用来确定你没有损害到现在已经工作的函数。这就是为什么你不应该修改那些已经通过的测试,除非是一些很小的修改,例如增加它的可读性(换句话说,分解测试)

  当一个测试非正常失败 有时你可能遇到失败的测试,而这时你对代码的改变是完全合理的。这通常是因为你遇到了冲突的需求。一般来说,可能是一个新的需求(一个改变的特性)与一个旧的可能已经不再有效的需求发生了冲突。这有两种可能:

  1.在旧的需求或者无效或者在别处测试的情况下删除被验证本质上不再有效的失败的测试

  2.改变旧的测试使你可以测试新的要求(本质上使用新的测试),然后在新的设置下(测试的逻辑状态相同,但是初始功能函数可能有所不同)测试旧的需求。

  而有时候一个测试在使用不完整的技术去完成任务的时候也是有效的,例如,你有一个成员类带有一个FOO方法,它表现为某几种行为,它已经经由Test 在X年前测试完成,然后现在一些其他的需求加了进来,方法的逻辑增强了,从而可以去处理一些类似于在获取数据时丢失一些参数的异常处理。但这时,突然 Test X失败了,虽然在测试这个函数的时候只是使用了同样的类。这个测试的失败是因为在调用方法之前丢失了一些初始处理步骤。

  这并不意味着你需要移除Test X,你将丢失对于一些重要功能的测试,这时你应该去关心那些初始化时的问题,而不是改变类的创建以用来适应你新的意图。

  当然如果你那里有200个测试都是因为旧的结构导致的失败,你就应该找到这个问题来维护你的测试。这就是为什么你应该总是移除你测试中的副本尤其是在生产代码中。

  测试覆盖和测试Angles 你如何知道是否你的新代码是一个好的覆盖?当试图移动一个链接或者一个约束检查后,如果所有的测试依然通过,那么你就没有足够的代码复制然后你可能需要添加其他的测试单元。

  确认你添加正确测试的最好方法就是测试一些最平常的行和检查直到用非常的手段使它出错。这个也许很难,但是如果你不能考虑出一个让代码出错的方法,你就可能没有好的理由在最初的地方写下这行代码。

  你不知道什么时候下一个开发者会试图运行你的程序,他可能优化或者错误的删除一些包含本质的行。如果你没有一个测试,它就会失败,其他的开发者可能不会知道他们犯了错误。

  你也可能试图利用一些常量去替代一些已经通过了的测试中调用的各种各样的参数,例如,看下面的方法:

Public Function Sum(ByVal x As Integer, ByVal y As Integer, _
ByVal allowNegatives As Boolean) As Integer
If Not allowNegatives Then Throw New Exception()
Return x + y
End Function

原文转自:http://www.uml.org.cn/Test/200605091.htm