如何阅读/提高PHP计算的C.R.A.P指数

78

我刚开始使用PHPUnit和其具有色彩的代码覆盖报告。我理解其中所有的数字和百分比,但唯独不明白C.R.A.P指数是什么意思以及如何分析它以及如何降低它。请问有人可以给我一个详细的解释吗?

2个回答

113

@Toader Mihai提供了一个扎实的解释。(我给他点赞)

如何降低代码质量:

写出更简单的代码或者进行更好的测试。(参见下面的图表)

什么是更好的测试?

在这个上下文中,这意味着:更高的代码覆盖率,通常会导致编写更多的测试。

什么是更简单的代码?

例如:将你的方法重构成小的模块:

// Complex
function doSomething() {
    if($a) {
        if($b) {
        }
        if($c) {
        }
    } else {
        if($b) {
        }
        if($c) {
        }
    }
}

// 3 less complex functions
function doSomething() {
    if($a) {
        doA();
    } else {
        doNotA();
    }
}

function doA() {
    if($b) {
    }
    if($c) {
    }
}

function doNotA() {
    if($b) {
    }
    if($c) {
    }
}

这只是一个微不足道的例子,你一定会找到更多相关资源的。

其他资源:

首先,让我提供一些额外的资源:

创建者关于 crap index 的博客文章

以防万一:圈复杂度的解释。像 PHP_CodeSniffer 和 PHPMD 这样的工具会告诉你这个数字,以防你想知道它。

虽然你可以自己决定什么数字算是“好”的,但通常建议的数字(在我看来有点高)是 30,其结果是以下的图形:

alt text (你可以在这里获取 .ods 文件:https://www.dropbox.com/s/3bihb9thlp2fyg8/crap.ods?dl=1


2
这是一张图像,最多显示5个为绿色,6-10个为黄色,超过10个为红色:http://i.imgur.com/wwX1TbZ.png - dave1010
@edorian,.ods链接已经失效了。你有新的链接可以提供吗? - Niko9911
1
@Niko9911 更新了链接。 - edorian

66
基本上,它希望成为方法变更风险的预测器。
它有两个因素:
1. 方法的代码复杂度(圈复杂度)即该方法中存在多少决策路径:comp(m)。 2. 该方法的可测试性(通过由代码覆盖工具提供的自动化测试)。基本上,这衡量了在所述代码中有多少决策是可以自动测试的。
如果该方法具有100%的覆盖率,则认为变更风险仅与该方法的复杂性等价:C.R.A.P.(m) = comp(m)。
如果该方法具有0%的覆盖率,则认为变更风险是复杂性度量的二次多项式(因为如果您无法测试代码路径,则更改会增加破坏的风险):C.R.A.P.(m) = comp(m)^2 + comp(m)
希望这能帮到您。
我刚注意到我只提供了一半的答案(读取部分)。如果您理解指数的推理,那么如何改进应该非常清楚。但是@edorian's answer中提供了更清晰的解释。
简而言之,编写测试直至接近100%的覆盖率,然后重构方法以减少圈复杂度。您可以尝试在进行测试之前进行重构,但是根据实际的方法复杂性,如果您无法理解所做更改的所有后果(由于涉及到的复杂性),则会冒着引入破坏的风险。

1
它没有考虑到依赖项。一个简单的 function example() { $dep = new Dependency(); return $dep->someFunction(); }function crappy($param) { switch ($param) { // 30 different cases with if-elses } } 更难测试(使用模拟逻辑可能会非常复杂,特别是在 PHP 中)。 - Juha Untinen

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接