Rob*_*ert 3 testing perl code-coverage devel-cover
我有这个函数,它接受一个数组,计算每个项目出现的频率,并返回一个唯一项目的数组,首先按计数排序,然后按字母顺序排序,然后按字母顺序不区分大小写,以便在运行之间顺序不会改变。
use strict;
use warnings;
sub sorted {
my @elements = @_;
my %counts;
foreach my $e (@elements) {
$counts{$e}++;
}
my @sorted = sort {
$counts{$b} <=> $counts{$a} or $a cmp $b or lc $a cmp lc $b
} keys %counts;
return @sorted;
}
1;
Run Code Online (Sandbox Code Playgroud)
我有这个测试用例,一切正常:
use strict;
use warnings;
use Test::More;
use module;
is_deeply(['A', 'a', 'c', 'b'], [sorted('a', 'b', 'c', 'a', 'c', 'A', 'A')]);
done_testing();
Run Code Online (Sandbox Code Playgroud)
我运行它并用于Devel::Cover
收集测试覆盖率数字。我期望 100% 的覆盖率,但分支和条件覆盖率很短:
HARNESS_PERL_SWITCHES=-MDevel::Cover prove -I. test.t && cover
test.t .. ok
All tests successful.
Files=1, Tests=1, 1 wallclock secs ( 0.03 usr 0.00 sys + 0.22 cusr 0.02 csys = 0.27 CPU)
Result: PASS
Reading database from ./cover_db
--------- ------ ------ ------ ------ ------ ------ ------
File stmt bran cond sub pod time total
--------- ------ ------ ------ ------ ------ ------ ------
module.pm 100.0 50.0 66.6 100.0 n/a 0.2 90.4
test.t 100.0 n/a n/a 100.0 n/a 99.8 100.0
Total 100.0 50.0 66.6 100.0 n/a 100.0 94.8
--------- ------ ------ ------ ------ ------ ------ ------
Run Code Online (Sandbox Code Playgroud)
检查HTML报告,它显示一些分支和条件没有被覆盖:
我不明白为什么Devel::Cover
认为某些分支和条件没有被涵盖。
它抱怨 TF 的分支没有被覆盖,这将是<=>
永远不真实的部分?我有两次“a”和“c”,因此<=>
当它比较“a”计数(2)与“b”计数(1)时,应该返回零(F)和非零(T)。
对于条件承保,报告称,支票的两个部分都是错误的情况不包括在内。再说一次,我认为我应该涵盖这一点,因为我有相同的计数和相同的名字。
我需要添加什么测试用例才能获得 100% 的分支和条件覆盖率?
或者,如果sort
这样的函数对于 来说很棘手Devel::Cover
,我如何告诉它忽略这些?我将代码更改为
my @sorted = sort {
# uncoverable branch left
# uncoverable condition true
$counts{$b} <=> $counts{$a} or $a cmp $b or lc $a cmp lc $b
} keys %counts;
Run Code Online (Sandbox Code Playgroud)
但这确实得到了相同的结果。
覆盖范围的问题在于,它所比较的两个项目的计数永远不会相同(条件<=>
为0
),并且它们相同(第一个cmp
条件为0
)。
为此,我们需要将一个元素与其自身进行比较,但排序例程使用的是频率计数中的键,而不是数组元素——因此任何一个元素中都不存在两个!因此,一个元素永远不会与其自身进行比较,并且前两个条件永远不会同时失败。
\n一种解决方案:按实际元素排序,然后选择唯一的元素。
\n至于分支故障,我现在还不能完全确定,但一个实用的(有效的)解决方案是取消这些测试。总共\xe2\x80\xa0
\npackage TestMod;\n\nuse strict;\nuse warnings; \nuse List::Util qw(uniq);\n\nsub sorted {\n my @elements = @_;\n\n my %counts;\n foreach my $e (@elements) {\n $counts{$e}++;\n }\n\n my @sorted = sort { \n my $cmp;\n\n if ( my $nc = $counts{$b} <=> $counts{$a} ) {\n $cmp = $nc\n }\n elsif ( my $ac = $a cmp $b ) {\n $cmp = $ac\n }\n else { $cmp = lc $a cmp lc $b }\n\n $cmp;\n } @elements;\n\n return uniq @sorted;\n}\n\n1;\n
Run Code Online (Sandbox Code Playgroud)\n现在我明白了
\nmain_TestMod.pl .. ok \nAll tests successful.\nFiles=1, Tests=1, 0 wallclock secs ( 0.02 usr 0.01 sys + 0.29 cusr 0.02 csys = 0.34 CPU)\nResult: PASS\nReading database from .../test_coverage/cover_db\n\n\n--------------- ------ ------ ------ ------ ------ ------ ------\nFile stmt bran cond sub pod time total\n--------------- ------ ------ ------ ------ ------ ------ ------\nTestMod.pm 100.0 100.0 n/a 100.0 0.0 2.5 97.3\nmain_TestMod.pl 100.0 n/a n/a 100.0 n/a 97.4 100.0\nTotal 100.0 100.0 n/a 100.0 0.0 100.0 98.3\n--------------- ------ ------ ------ ------ ------ ------ ------\n\n\nHTML output written to .../test_coverage/cover_db/coverage.html\ndone.\n
Run Code Online (Sandbox Code Playgroud)\n(我的系统上的实际路径被抑制)
\n注意——现在根本没有条件。FWIW:当我留下一个大的、典型的sort
多重or
条件时(在对元素排序时,而不是频率哈希键),那么该条件确实具有 100% 的覆盖率。但分支失败了。
\xe2\x80\xa0在这种直接连续测试且没有其他处理的情况下,我们也可以在每个分支中返回(其中的块sort
是一个匿名子块,可以return
)
package TestMod;\n\nuse strict;\nuse warnings; \nuse List::Util qw(uniq);\n\nsub sorted {\n my @elements = @_;\n\n my %counts;\n foreach my $e (@elements) {\n $counts{$e}++;\n }\n\n my @sorted = sort { \n if ( my $nc = $counts{$b} <=> $counts{$a} ) {\n return $nc\n }\n elsif ( my $ac = $a cmp $b ) {\n return $ac\n }\n else { \n return lc $a cmp lc $b \n }\n } @elements;\n\n return uniq @sorted;\n}\n\n1;\n
Run Code Online (Sandbox Code Playgroud)\n
归档时间: |
|
查看次数: |
154 次 |
最近记录: |