跳转至

23 传统应用程序测试

说明

本文档由 AI 生成

这一章(Chapter 23: Testing Conventional Applications)非常扎实,它深入讲解了**传统应用程序的测试 (Testing Conventional Applications)。与上一章宏观的测试策略不同,这一章聚焦于**具体的测试用例设计技术 (Test Case Design Techniques)

这一章的逻辑非常清晰:首先定义了什么是**可测试性 (Testability)** 和**好的测试 (Good Test),然后阐述了**内部视图 (White-box) 与**外部视图 (Black-box)** 的区别;接着,核心内容详细讲解了**白盒测试**中的逻辑覆盖、基本路径测试 (Basis Path Testing) 和循环测试 (Loop Testing);最后,全面覆盖了**黑盒测试**的各种方法,包括等价类划分、边界值分析、基于图的方法以及正交数组测试等。

以下是为你整理的详细笔记(Markdown格式),专有名词后均已附上英文对照,非常适合用来复习备考。


🧪 软件工程 Chapter 23: 传统应用程序测试 (Testing Conventional Applications)

1. 可测试性 (Testability)

  • 定义: 软件能够被有效且高效测试的程度。
  • 关键属性 (Attributes):
    • 可操作性 (Operability): 软件运行越顺畅,测试越容易进行。
    • 可观察性 (Observability): 每个测试用例的结果都易于被观察到。
    • 可控性 (Controllability): 测试被自动化和优化的程度。
    • 可分解性 (Decomposability): 测试可以被精准定位 (Targeted)。
    • 简单性 (Simplicity): 降低复杂的架构和逻辑以简化测试。
    • 稳定性 (Stability): 测试期间需求变更较少。
    • 可理解性 (Understandability): 对设计的理解程度。

2. 什么是“好的”测试?(What is a "Good" Test?)

  • 高概率发现错误: 一个好的测试具有很高的概率找到尚未发现的错误。
  • 非冗余 (Not redundant): 每个测试都应该有其独特的目的,不应该是重复的。
  • “优中选优” ("Best of breed"): 在一组相似的测试中,应选择那个最能代表该组特征或最可能发现问题的测试。
  • 适度复杂: 既不要太简单也不要太复杂。

3. 内部视图 vs. 外部视图 (Internal and External Views)

  • 外部视图 (Black-box / Functional):
    • 基于产品设计的功能进行测试。
    • 目标:证明每个功能都是可操作的,并在功能中寻找错误。
  • 内部视图 (White-box / Structural):
    • 基于产品的内部工作机制进行测试。
    • 目标:确保“所有齿轮都啮合”,即内部操作符合规范,所有内部组件都被充分执行。

4. 测试用例设计基础 (Test Case Design)

  • 核心目标 (Objective): 发现错误 (Uncover errors)。
  • 准则 (Criteria): 以完整的方式 (Complete manner) 进行。
  • 约束 (Constraint): 在最少的努力和时间 (Minimum of effort and time) 下完成。
  • 贝izer定律 (Boris Beizer): “Bug潜伏在角落里,并聚集在边界上 (Bugs lurk in corners and congregate at boundaries)。” —— 这句话是边界值分析的理论基础。

5. 白盒测试 (White-Box Testing)

  • 目标: 确保所有语句和条件至少被执行一次。
  • 为什么要覆盖?(Why Cover?):
    • 逻辑错误和不正确的假设与路径的执行概率成**反比** (Inversely proportional)。我们往往认为不太可能执行的路径,实际上却经常发生。
    • 排版错误 (Typographical errors): 是随机的,未测试的路径很可能包含此类错误。

6. 基本路径测试 (Basis Path Testing)

这是一种旨在测试程序中所有独立执行路径的方法。

  • 步骤 1:计算圈复杂度 (Cyclomatic Complexity, V(G)):
    • 公式:流图中的封闭区域数 + 1。
    • 意义: 圈复杂度的值等于需要执行的独立路径的数量。
    • 行业指标: V(G) 越高,模块出错的概率越高。
  • 步骤 2:推导独立路径 (Independent Paths):
    • 根据圈复杂度的数值,找出对应的独立路径集合。
    • 例如:若 V(G)=4,则有 4 条独立路径。
  • 步骤 3:设计测试用例:
    • 准备能够强制执行上述每一条路径的测试用例。
  • 注意事项:
    • 不一定需要画流程图,但画图有助于追踪路径。
    • 复合逻辑测试 (Compound tests) 算作 2 个或更多。
    • 应用于**关键模块 (Critical modules)**。

7. 图矩阵 (Graph Matrices)

  • 定义: 一种方阵,其大小等于流图中节点的数量。
  • 结构: 每一行和每一列对应一个节点,矩阵项对应节点之间的连接 (边)。
  • 用途: 通过为矩阵项添加连接权值 (Link weight),图矩阵可以成为评估程序控制结构的强大工具。

8. 控制结构测试 (Control Structure Testing)

  • 条件测试 (Condition testing): 练习程序模块中包含的逻辑条件。
  • 数据流测试 (Data flow testing):
    • 根据程序中变量的**定义 (Definitions)** 和**使用 (Uses)** 位置来选择测试路径。
    • DU 链 (Definition-Use chain): 形如 [X, S, S'] 的链,其中 S 定义了变量 X,S' 使用了变量 X,且 S 中对 X 的定义在 S' 处是活跃的。

9. 循环测试 (Loop Testing)

这是白盒测试中非常实用的技术,针对不同类型的循环设计测试用例。

循环类型 (Loop Type) 测试策略 (Strategy)
简单循环 (Simple Loop) 1. 完全跳过循环 (Skip entirely)2. 只循环 1 次 (One pass)3. 循环 2 次 (Two passes)4. 循环 m 次 (m < n)5. 循环 n-1, n, n+1 次 (n为最大允许次数)
嵌套循环 (Nested Loops) 1. 从最内层循环开始,将所有外层循环设置为最小值。2. 测试最内层循环的 min+1, typical, max-1, max,同时外层保持最小值。3. 向外移动一层,重复步骤 2,直到测试完最外层。
串联循环 (Concatenated Loops) - 如果循环相互独立,作为简单循环处理。- 如果循环相关(例如循环 1 的计数器用于初始化循环 2),作为嵌套循环处理。
非结构化循环 (Unstructured Loops) 应该重新设计程序以使用结构化编程构造。

10. 黑盒测试 (Black-Box Testing)

  • 关注点: 基于需求、输入、输出和事件,不关心内部结构。
  • 核心问题:
    • 如何测试功能的有效性?
    • 如何测试系统行为和性能?
    • 哪些输入类能构成好的测试用例?
    • 系统对特定输入值是否敏感?
    • 如何隔离数据类的边界?
    • 系统能容忍的数据速率和数据量是多少?

11. 黑盒测试方法 (Black-Box Methods)

  • 基于图的方法 (Graph-Based Methods):
    • 理解软件中建模的对象 (Objects) 及其连接关系 (Relationships)。
    • 节点 (Node) 代表对象,边 (Link) 代表关系。
  • 等价类划分 (Equivalence Partitioning):
    • 将输入域划分为若干个**等价类 (Equivalence Classes)**,使得每个类中的一个代表值在测试中等同于该类中的所有其他值。
    • 有效数据 (Valid data): 符合程序规范的数据(如命令、文件名、计算数据)。
    • 无效数据 (Invalid data): 超出程序边界、物理上不可能或位置错误的数据。
  • 边界值分析 (Boundary Value Analysis, BVA):
    • 基于“Bug聚集在边界上”的原则。
    • 重点关注输入域和输出域的边界值 (Bounding values)。
  • 比较测试 (Comparison Testing):
    • 仅用于可靠性要求极高的系统 (Human-rated systems)。
    • 不同团队开发独立版本,使用相同数据测试,结果必须一致。
  • 正交数组测试 (Orthogonal Array Testing):
    • 适用于输入参数数量少且取值范围明确有界的情况。
    • 使用正交数组 (Orthogonal array, 如 L9) 来减少测试用例数量,同时保证覆盖率。
  • 基于模型的测试 (Model-Based Testing):
    • 分析或创建系统的**行为模型 (Behavioral model)**。
    • 遍历模型,指定触发状态转换 (State transition) 的输入,并验证输出。

12. 软件测试模式 (Software Testing Patterns)

  • 定义: 类似于设计模式,描述了在特定上下文中解决常见测试问题的方法。
  • 例子:场景测试 (Scenario Testing):
    • 目的: 在单元和集成测试之后,确定软件是否能以满足用户的方式执行。
    • 特点: 从用户的角度 (User's point of view) 来练习软件。
    • 失败含义: 此级别的失败意味着软件未能满足用户可见的需求。

💡 复习重点总结 (Key Takeaways for Exam)

  1. 基本路径测试 (Basis Path Testing): 这是计算题的高发区。必须掌握如何根据流程图计算**圈复杂度 (Cyclomatic Complexity),以及如何根据复杂度推导出**独立路径 (Independent Paths)
  2. 循环测试 (Loop Testing): 必须区分 简单循环 的测试步骤和 嵌套循环 的测试策略(从内向外)。
  3. 黑盒测试技术: 理解 等价类划分 (Equivalence Partitioning)边界值分析 (Boundary Value Analysis) 的区别与联系(BVA通常作为等价类划分的补充)。
  4. 术语辨析: 注意区分 White-box (关注内部逻辑/路径) 和 Black-box (关注外部功能/需求)。
  5. 测试原则: 记住 Boris Beizer 的名言:“Bugs lurk in corners...”,这解释了为什么我们要做边界值分析。
  6. 数据流测试: 理解 DU 链 (Definition-Use chain) 的概念,即变量在哪里定义,在哪里使用。

评论区

欢迎在评论区指出文档错误,为文档提供宝贵意见,或写下你的疑问