你怎么看待无所不在的“测试,测试,测试!”原理?

时间:2009-12-26 09:44:47

标签: debugging testing

在过去,编程习惯涉及较少的猜测。我会编写一些代码行,并且100%确定代码的作用以及它不会一目了然。错误主要是拼写错误,但与功能无关。

过去几年我认为这种“反复试验”编程有一种趋势:编写代码(就像在草稿中一样),然后迭代调试,直到程序的行为符合要求。测试,再次测试,然后再测试。 有趣的是,在我的Visual Studio中,“运行”按钮已被标记为“调试”的按钮所取代(=我知道你有一些错误!)。我不得不承认,在我编写的几个应用程序中,我无法保证无错误的代码。

你怎么看?或者我们的系统现在过于复杂(浏览器/操作系统/服务包兼容性等),这证明在所有类型的环境中都可以进行测试。

9 个答案:

答案 0 :(得分:9)

实际上,我经历了相反的情况。虽然它曾经是一个运行直到它工作的情况,我现在进行单元测试,直到测试通过...而且这似乎至少是一个合理的共同过渡,据我所见。

我不得不说第一次只使用拼写错误的代码从来没有在我的经验中是常态。不同的是,现在我可以更快地找到问题,并发现旧问题是否会出现。我有时可以管理非常短而简单的代码而没有错误(并且Stack Overflow上的帖子已经提高了这种能力)但是大而复杂的系统?哎呀。

要回答你的帖子的标题 - 在我看来,“测试,测试,测试”原则是一个很好的原则......但我并没有将其与重复运行整个程序联系起来。我经常将它与运行单元测试联系起来。我很少需要使用调试器进行单元测试 - 通常情况下失败会使检查结果变得非常明显,因为只测试了少量代码。

答案 1 :(得分:4)

可能是在后来的几年里,开发人员已经意识到“100%确定性”可能实际上并不正确吗?开发软件非常复杂,即使这些工具多年来不断发展,我们也意识到编写好的代码很难。确实,调试和自动化单元测试使我们更有效率,但我们仍然会产生错误,正如我们当时所做的那样,现在我们只有不同的工具来捕捉它们。

答案 2 :(得分:4)

你可以编写你认为100%知道它做了什么和不做什么的代码,但总有一个你没有想过的边缘情况或者你没想到的奇怪异常。有些时候,试验和错误编程可以成为缩小问题范围的有用工具,而调试器会提供帮助。

了解哪些工具可用于帮助生成具有最小错误的代码非常重要。

答案 3 :(得分:4)

我发现测试测试方法可以帮助我设计代码。有时,必须完成的工作太复杂,无法完成所有工作。测试迫使我把它分成更小的部分,当我解决这些问题时,我能够将它们组合成一个更大的整体。

答案 4 :(得分:4)

单词答案是“复杂性”。真正的答案是“不必要的复杂性”! 会计原则在过去30年中没有改变。为什么今天编写会计系统要困难得多?有一个图形用户界面是好的,但我们是否必须过火?

多年来,软件开发陷入了恶性循环。复杂性正在自我提供,而不是减少它,我们只是将它隐藏在层和包装层之下。最终会发生一些事情。

当我们赞成形式超过功能时,我们必须付出代价。

答案 5 :(得分:4)

我认为优势来自间接方式:当您接受测试和单元测试时,您必须以可以实际编写测试的方式编写应用程序:

  • 需要以这样的方式编写类,即可以在没有整个应用程序和操作系统的情况下实例化单个对象,而只需要几个辅助对象。这意味着您需要最小化依赖关系,并明确与周围系统的所有通信。

  • 实现测试用例意味着您必须找到最小的命令和调用序列,以使您的类执行有意义的操作。这通常表明设计决策很尴尬,或者表明类很难用于某些目的。

总而言之,当您接受测试时,您最终会得到一个系统,其组件之间的相互依赖性最小,而测试用例则作为如何使用组件的文档。

答案 6 :(得分:3)

测试(执行你的系统)会告诉你一些关于“存在错误但不存在错误”的信息(afaik这个术语由dijkstra推算)。它指出了测试套件的强度是测试关键的方向:“你可以说有很多测试用例,很多bug都不存在。这意味着你的软件的大部分工作都按预期工作”

有一个强大/强大的测试套件的一些例子:

  • 许多代码由您的单元测试(传统的覆盖术语)执行
  • 您没有假阴性测试(测试显示绿色但实际上应该是红色)。假阴性测试是邪恶的,因为它们会给你一种错误的测试用例质量感。有关良好的测试断言和假阴性的详细信息,另请参阅blog-entry#1blog-entry#2
  • 这些要求很好理解(我已经看到很多情况下,自动化测试是在测试错误的东西而开发人员误解了业务的要求)。因为开发人员是绿色的,但对于企业来说,系统没有按预期工作(另一种假阴性的例子,但在更高层次上)。

从某种意义上说,程序的正确性只有在用数学证明完成时才能得到证实(这只能为生命攸关的和资金紧张的系统付出代价)。您仍然可以通过自动化测试获得很多(除了单元测试,自动化集成测试总能帮助很多)。

关于调试:我像以前一样经常使用调试,但有时在向代码添加新功能时(我的新测试用例显示为绿色)我打破了其他测试用例。通过断言我立即看到出了问题,但仍未找到错误。对于定位错误,调试仍然有用(使用红色测试用例,我执行有问题的代码路径,使用调试器找到错误)。

如果您对测试自动化感兴趣,请查看杰作xUnit Test patterns

答案 7 :(得分:1)

我读过一本书(肯特贝克的“TDD示例”)确实似乎把“试错”的方法推向极端:但它更像是“让单元测试工作”。尽管如此,我仍然无法完成这本书 - 这是一个罕见的事件,特别是因为我真的希望得到一个更好的理解。尽管如此,提交明显低级的代码以后会有所改进让我颤抖。

科学:自动化测试有其优势。然而,它们并不是他们声称的银弹。没有一种测试方法足以发现缺陷,其他方法具有更好的检测率。

直觉:我们的问题是日益复杂的问题。复杂性与我们必须管理的代码量高度相关。有鉴于此,TDD尝试通过编写甚至更多的代码来解决到更多代码的问题。

优势:我们现在已经建立了形式主义,使测试可重复,负责并立即记录。这绝对是一种摆脱“在我的机器上工作”和“奇怪,它昨天工作,我会给你最新的DLL”陷阱的方法。

答案 8 :(得分:0)

我目前正在练习测试驱动开发(TDD),或至少编写许多单元测试来验证我的大部分/全部代码的行为方式与我期望它的行为方式相同。采用这种方法迫使我从消费者的角度来看待我的计划。此外,在我编写测试时,我经常会想到边界限制,我最初没想到的其他场景等等。

我现在已经到了我不敢改变旧程序的地步,因为我担心我会破坏某些东西。与运行一系列单元测试相比,回归测试非常繁琐。