判定覆盖
这种度量报告的是在控制结构里(例如IF语句和WHILE语句)的布尔表达式的真假值都被测过了。整个的布尔表达式被看成了一个单独的真假判定,不管它里面有没有逻辑与或者逻辑非操作符。这种覆盖还包括了SWITCH语句里的CASE执行语句,EXCEPTION处理,以及中断处理的覆盖。
它也被叫做分支覆盖,all-edges(所有边界?)覆盖[Roper1994 p.58], 基本路径覆盖[Roper1994 p.48], C2 [Beizer1990 p.75], DDP覆盖(判定路径覆盖)[Roper1994 p.39].“基本路径”测试是选择相应的路径去满足判定覆盖。
我不推荐使用C2这个描述不清楚的名字,它容易和术语C1搞混。
这种覆盖的优点就是简单,以及没有语句覆盖的那些问题。缺点就是会由于布尔表达式里面的short-circuit 操作符,而忽略掉一些分支。比如下面的C/C++/JAVA代码段:
if (condition1 && (condition2 || function1()))
statement1;
else
statement2;
在使用这种度量方法考虑覆盖率分析的时候,可以完全不考虑调用function1()而达到完全覆盖。当condition1和condition2都取真值的时候,整个表达式就真,当condition1为假的时候,整个表达式就为假。在这种情况下,short-circuit 操作符把调用function1排除在外。
条件覆盖
条件覆盖报告了每一个被逻辑非和逻辑与分开的布尔子表达式真假值的情况。条件覆盖独立的估量每个子表达式。
这种度量与判定覆盖相似,但对控制流的敏感性又比它强。但是,完全条件覆盖并不能保证完全的判定覆盖。比如下面的C++/JAVA代码例子:
bool f(bool e) { return false; }
bool a[2] = { false, false };
if (f(a && b)) ...
if (a[int(a && b)]) ...
if ((a && b) ? false : false) ...
在上面的例子中,不管a和b的值取什么,所有的IF语句都会走假分支。但是,如果你使用了所有的a和b值的组合去测试代码,条件覆盖会报告完全覆盖的结果。
多条件覆盖
多条件覆盖是报告是否所有布尔子表达式的组合都出现了。在前面介绍条件覆盖的时候,子表达式都是被逻辑与逻辑非分开的。
如果想要达到对一个条件的多条件完全覆盖的话,可以由这个条件的逻辑操作符真值表来获得。
对于有short-circuit操作符的语言来说,像C,C++,和JAVA,多条件覆盖有一个优点就是它需要非常彻底的测试。对于这些语言来讲,多条件覆盖和条件覆盖非常相像。
这种度量的缺点就是决定所需最小测试用例集的过程是非常冗长的,尤其对于非常复杂的布尔表达式来说,更乏味。
它的另一种缺点就是对于相似复杂度的条件,它们所需要的测试用例数相差可以相当的大。比如下面的两个C/C++/JAVA条件的例子:
1st a && b && (c || (d && e))
2nd ((a || b) && (c || d)) && e
为了得到完全的多条件覆盖,第一个例子里的条件需要6个测试用例,第二个需要11个。这两个例子具有相同数量的操作数和操作符。
下面是测试用例的列表。
a && b && (c || (d && e))
1. F - - - -
2. T F - - -
3. T T F F -
4. T T F T F
5. T T F T T
6. T T T - -
((a || b) && (c || d)) && e
1. F F - - -
2. F T F F -
3. F T F T F
4. F T F T T
5. F T T - F
6. F T T - T
7. T - F F -
8. T - F T F
9. T - F T T
10. T - T - F
11. T - T - T
多条件覆盖和条件覆盖一样不包括判定覆盖。对于没有short-circuit操作符的语言,比如VB和PASCAL,多条件覆盖是一种有效的逻辑表达试的路径覆盖,它有一样的优缺点。下面是VB的代码例子。