什么是测试驱动开发 (TDD)?示例

什么是测试驱动开发 (TDD)?

测试驱动开发 (TDD) 是一种软件开发方法,其中开发测试用例来指定和验证代码将执行的操作。简而言之,首先创建并测试每个功能的测试用例,如果测试失败,则编写新代码以通过测试并使代码简单且无错误。

测试驱动开发从设计和开发应用程序每个小功能的测试开始。TDD 框架指示开发人员仅在自动化测试失败时才编写新代码。这避免了代码重复。TDD 的全称是测试驱动开发。

测试驱动开发

TDD 的简单概念是在编写新代码之前(开发之前)编写并纠正失败的测试。这有助于避免代码重复,因为我们每次只编写少量代码以通过测试。(测试不过是我们需要测试以满足其要求的条件)。

测试驱动开发是在实际开发应用程序之前开发和运行自动化测试的过程。因此,TDD有时也称为 测试优先开发。

如何进行 TDD 测试

以下步骤定义了如何执行 TDD 测试,

  1. 添加测试。
  2. 运行所有测试并查看是否有任何新测试失败。
  3. 写一些代码。
  4. 运行测试并重构代码。
  5. 重复。
执行 TDD 测试
测试驱动开发的五个步骤

TDD 周期定义

  1. 编写测试
  2. 使其运行。
  3. 更改代码使其正确,即重构。
  4. 重复过程。

关于 TDD 的一些说明:

  • TDD 方法既与“测试”无关,也与“设计”无关。
  • TDD 并不意味着“编写一些测试,然后构建一个通过测试的系统”。
  • TDD 并不意味着“进行大量测试”。

TDD 与传统测试

以下是测试驱动开发和传统测试之间的主要区别:

TDD 方法主要是一种规范技术。它可确保您的源代码在确认级别得到彻底测试。

  • 对于传统测试,成功的测试会发现一个或多个缺陷。这与 TDD 相同。当测试失败时,您已经取得了进展,因为您知道需要解决问题。
  • TDD 可确保您的系统真正满足为其定义的要求。它有助于建立您对系统的信心。
  • 在 TDD 中,更多的关注点在于验证测试是否正常工作的生产代码。在传统测试中,更多的关注点在于测试用例设计。测试是否会显示应用程序的正确/不正确的执行以满足要求。
  • 在 TDD 中,您可以实现 100% 覆盖率测试。与传统测试不同,每一行代码都经过测试。
  • 传统测试与TDD的结合导致了系统测试的重要性而不是系统的完善性。
  • In 敏捷建模(AM),你应该“有目的地进行测试”。你应该知道为什么要测试某些东西以及需要进行什么级别的测试。

什么是验收TDD和开发人员TDD

TDD 有两个级别

  1. 验收测试驱动开发 (ATDD): 使用 ATDD,您可以编写单个验收测试。此测试满足规范的要求或满足系统的行为。之后,只需编写足够的生产/功能代码即可完成该验收测试。验收测试侧重于系统的整体行为。ATDD 也被称为 行为驱动开发 (BDD).
  2. 开发人员 TDD: 使用开发人员 TDD,您可以编写单个开发人员测试(即单元测试),然后编写足够的生产代码来完成该测试。单元测试侧重于系统的每个小功能。开发人员 TDD 简称为 TDD。ATDD 和 TDD 的主要目标是在即时 (JIT) 的基础上为您的解决方案指定详细的可执行需求。JIT 意味着只考虑系统所需的需求。从而提高效率。

验收 TDD 和开发人员 TDD

通过敏捷模型驱动开发 (AMDD) 扩展 TDD

TDD 非常擅长详细规范和验证。它无法考虑更大的问题,例如整体设计、系统使用或 UI。AMDD 解决了 TDD 无法解决的敏捷扩展问题。

因此 AMDD 用于解决更大的问题。

AMDD 的生命周期

AMDD 的生命周期

在模型驱动开发 (MDD) 中,在编写源代码之前会创建大量模型。这反过来又具有敏捷方法?

在上图中,每个框代表一项开发活动。

设想是 TDD 流程之一,用于预测/想象将在项目第一周进行的测试。设想的主要目标是确定系统范围和系统架构。高级需求和架构建模是为了成功设想而完成的。

该过程不是对软件/系统进行详细规范,而是探索软件/系统的需求,从而定义项目的总体策略。

迭代 0:展望

主要有两个子激活。

  1. 初步需求设想。确定系统的高级需求和范围可能需要几天的时间。主要重点是探索使用模型、初始域模型和用户界面模型 (UI)。
  2. 初始 Archi建筑设想。 确定系统架构也需要几天时间。它允许为项目设定技术方向。主要重点是探索技术图表、用户界面 (UI) 流程、领域模型和变更案例。

迭代建模

在这里团队必须规划每次迭代要完成的工作。

  • 每次迭代都采用敏捷过程,即每次迭代过程中,都会优先添加新的工作项。
  • 首先将考虑优先级较高的工作。添加的工作项目可能会随时重新确定优先级或从项目堆栈中删除。
  • 团队讨论如何实现每个需求。建模就是为了实现这个目的。
  • 针对该迭代中要实现的每个需求进行建模分析和设计。

模型风暴

这也称为即时建模。

  • 这里的建模会议涉及 2/3 成员组成的团队,他们在纸上或白板上讨论问题。
  • 一名团队成员将邀请另一名成员与其一起建模。此建模过程大约需要 5 到 10 分钟。团队成员聚在一起共享白板/纸张。
  • 他们不断探索问题,直到找不到问题的主要原因。如果一名团队成员发现了他/她想要解决的问题,那么他/她会迅速寻求其他团队成员的帮助。
  • 然后其他小组成员探讨该问题,然后每个人继续像以前一样。这也被称为站立式建模或客户 QA 会议。

测试驱动开发 (TDD)

  • 它促进对您的应用程序代码和详细规范的确认测试。
  • 验收测试(详细需求)和开发人员测试(单元测试)都是 TDD 的输入。
  • TDD 使代码更简单、更清晰。它允许开发人员维护更少的文档。

评价

  • 这是可选的。它包括代码检查和模型审查。
  • 这可以针对每次迭代或整个项目进行。
  • 这是为项目提供反馈的一个很好的选择。

测试驱动开发 (TDD) 与敏捷模型驱动开发 (AMDD)

TDD 高级诊断
TDD 缩短了编程反馈循环 AMDD 缩短了建模反馈循环。
TDD 是详细规范 AMDD 解决更大的问题
TDD 促进高质量代码的开发 AMDD 促进与利益相关者和开发人员的高质量沟通。
TDD 与程序员对话 AMDD 采访 商业分析师、利益相关者和数据专业人员。
TDD 非视觉导向 AMDD 视觉导向
TDD 的范围仅限于软件工作 AMDD 的范围很广,包括利益相关者。它涉及努力达成共识
两者都支持进化发展 ---------------

TDD 框架

以下是最佳测试驱动开发 (TDD) 框架的列表

  1. 朱尼特
  2. TestNG
  3. csUnit 和 NUnit
  4. 规范

现在,让我们通过示例学习测试驱动开发。

TDD 示例

在此测试驱动开发示例中,我们将定义一个类密码。对于此类,我们将尝试满足以下条件。

密码接受条件:

  • 密码应介于 5 到 10 个字符之间。

首先在这个TDD示例中,我们编写满足上述所有要求的代码。

TDD 示例

情景1:为了运行测试,我们创建类PasswordValidator();

TDD 示例

我们将运行上面的类TestPassword();

输出已通过,如下所示;

输出:

TDD 示例

情景2:这里我们可以看到,在方法 TestPasswordLength() 中,不需要创建 PasswordValidator 类的实例。实例意味着创建一个 对象 来引用该类的成员(变量/方法)。

TDD 示例

我们将从代码中删除 class PasswordValidator pv = new PasswordValidator ()。我们可以调用 已验证 () 方法直接 PasswordValidator.IsValid(“Abc123”)(见下图)

因此我们重构(更改代码)如下:

TDD 示例

情景3:重构后,输出显示失败状态(见下图),这是因为我们已删除该实例。因此没有对非静态方法的引用 已验证 ()。

TDD 示例

所以我们需要将此方法改为 public static boolean isValid (String password),在 Boolean 前添加“static”字样。重构类 PasswordValidator() 以消除上述错误,从而通过测试。

TDD 示例

输出:

对类 PassValidator () 进行更改后,如果我们运行测试,则输出将为 PASSED,如下所示。

TDD 示例

TDD 的优点

以下是软件工程中测试驱动开发的主要优点:

早期错误通知。

  • 开发人员测试他们的代码,但在数据库领域,这通常包括手动测试或一次性脚本。使用 TDD,您可以随着时间的推移构建一套自动化测试,您和任何其他开发人员都可以随时重新运行这些测试。

设计更好、更清晰、更具扩展性的代码。

  • 它有助于理解代码将如何使用以及它如何与其他模块交互。
  • 它可带来更好的设计决策和更易于维护的代码。
  • TDD 允许编写具有单一职责的较小代码,而不是具有多个职责的单片程序。这使得代码更易于理解。
  • TDD 还强制仅编写生产代码以根据用户要求通过测试。

重构的信心

  • 如果您重构代码,代码中可能会出现问题。因此,通过一组自动化测试,您可以在发布之前修复这些问题。如果使用自动化测试发现问题,则会发出适当的警告。
  • 使用 TDD,应该会产生更快、更具扩展性的代码,并且错误更少,并且可以以最小的风险进行更新。

有利于团队合作

  • 在没有团队成员的情况下,其他团队成员可以轻松接手并处理代码。它还有助于知识共享,从而使团队整体更有效率。

对开发者有利

  • 虽然开发人员必须花费更多时间编写 TDD 测试用例,但调试和开发新功能所需的时间却少得多。您将编写更简洁、更简单的代码。

结语

  • TDD 代表测试驱动开发。
  • TDD 含义:为了通过预先设计的测试而修改代码的过程。
  • 它更加注重生产代码而不是测试用例设计。
  • 测试驱动开发是为了通过先前设计的测试而修改代码的过程。
  • In 软件工程,有时也被称为 “测试优先开发”。
  • TDD 测试包括重构代码,即在不影响代码行为的情况下更改/添加一定量的代码到现有代码中。
  • 当使用TDD编程时,代码会变得更加清晰和简单易懂。