About Clover code metrics
Code coverage metrics
Branch coverage
Statement coverage
Method coverage
Total Coverage Percentage (Coverage %, TPC)
The Total Coverage Percentage is calculated as follows:
TPC = (BT + BF + SC + MC)/(2*B + S + M) * 100%
where
BT - branches that evaluated to "true" at least once
BF - branches that evaluated to "false" at least once
SC - statements covered
MC - methods entered
B - total number of branches
S - total number of statements
M - total number of methods
Code complexity metrics
Average Method Complexity (Avg Method Cmp)
The average method complexity of code in the given context. In case of:
- classes: Average Method Complexity = sum of Method Complexity of all class' methods / number of methods in a class
- packages: Average Method Complexity = sum of Method Complexity of all package's methods / number of methods in a package
- project: Average Method Complexity = sum of Method Complexity of all project's methods / number of methods in a project
Complexity (Cmp, Total Cmp)
Cyclomatic complexity of code in the given context.
Method Complexity
Cyclomatic complexity of a single method. It's calculated as follows:
- empty method complexity == 1
- simple statement complexity == 0
- switch block complexity == number of case statements
- try catch block complexity == number of catch statements
- ternary expression complexity == 1
- boolean expression complexity == number of && or || in expression
Complexity Density (Cmp Density)
Complexity Density is the average number of paths in your code per statement in given context (method, class, package). It's calculated as follows:
Cmp Density = Complexity / number of statements
LOC
Lines Of Code (including comment lines).
NCLOC
Non-Commented Lines Of Code. Lines of code that contain comments are not counted in this metric, leaving only the actual functioning code itself.
Clover currently does not calculate NCLOC for Groovy code (CLOV-1805).
Examples
// # of statements, # of branches, Method Cyclomatic Complexity
// 0, 0, 1
void A() {}
// 1, 0, 1
void A() { a(); }
// 1 ,0 ,1
void A() { a = (6 < 7); }
// 3, 0, 1
void A() { a(); b(); c(); }
// 3, 2, 2
void A() { if (a()) b(); else c(); }
// 2, 2, 3
void A() { if (a() || b()) c(); }
// 2, 0, 1
void A() { if (1 + 2 == 4) c(); }
// 2, 2, 2
void A() { for (; a(); ) b(); }
// 2, 2, 3
void A() { for (; a() || b(); ) c(); }
// 2, 0, 1
void A() { for (; 1 + 2 == 4; ) c(); }
// 2, 2, 2
void A() { while (a()) b(); }
// 2, 2, 3
void A() { while (a() || b()) c(); }
// 2, 0, 1
void A() { while (1 + 2 == 4) c(); }
// 3, 0, 2
void A() { switch (a()) { case 1: b();} }
// 5, 0, 3
void A() { switch (a()) { case 1: b(); case 2: c();} }
// 1, 2, 2
void A() { a() ? 1 : 2; }
// 1, 2, 3
void A() { a() || b()? 1 : 2; }
// 1, 6, 4
void A() { a() ? b() ? c()? 1 : 2 : 3 : 4; }
References