More Than One Quarter Iffy
Fri 2007-09-14 14:59
Sometimes I'm subjected to code that is a joy to read… alas, such times
are very few and very far between. I was deciphering some code today and
thought the "signature" of the nesting could be interesting, I'm sure there
must be tools that give some pointless metric on such things (It should be a
web tool/competition:
"Congratulations! Your code has a nesting factor of one million! You'll receive your DIY-Euthanasia kit in the mail shortly!").
Maybe we need an "iffy factor", ratio of ifs (counting if, else if,
and else lines) to lines of code (the "simple iffy metric") multiplied by
average if statement nest depth (full iffy metric), or something.
Anyway, no time to think about it further right now but I thought I'd share the
love:
For consistency and ease of processing in this measurement I think the code
should be put through a formatter first, such as indent. Then I
extracted/anonymised flow control lines:
indent -kr -l1000 -nut < nestmania.c | \
grep '^ *\(if\|else\|while\|for\|}\|{\)' | \
sed 's/[[:alnum:]_]*([^()]*)/()/g'
And saw this:
{ while () { if (() && ()) { if () { if () { } else { if () { if () { if (() == -1) { } if () { } } } if () { if () { if () { } } else { } } } } if (() && ()) { if () { if () { } else { if () { if (() == -1) { } if () { } } if () { if () { if () { } } else { } } } } if (() && ()) { if () { if () { } else { if () { if () { if () { if () { if (() == -1) { } } if () { } } } } else { } } } } if (() && ()) { if () { if () { } else { if () { } else { } } } } if (() && ()) { if () { if (() == -1) { } if () { if () { } } else { } } } if (() && ()) { if () { if (() == -1) { } if () { } } } } }
That's 50 if/else lines (lines with just } aren't counted). The whole
function is 191 lines long (again not counting } and also not counting
comments). So this function is more than one quarter iffy by the simple
iffy metric. For the full iffy metric I'll take the average of the
indent depth (counting "indents" not "spaces") of if lines, this is 4.41463,
and calculate: (50/191) x 4.41463 = 1.16
So maybe anything over 0.5 needs to be thought through again, and anything over
1.0 needs serious reconsideration. It probably makes more sense to apply to
single functions, or maybe even just single top-level if statements.
This is not the most iffy feeling code I've come across.
The entire metric is certainly flawed :) but I'm not going to waste time
thinking about it any more, I've got iffy code to get back to!
[[[ BTW: The colouring was done with the suitably horrific:
indent -kr -l1000 -nut < nestmania.c | \
grep '^ *\(if\|else\|while\|for\|}\|{\)' | \
sed 's/[[:alnum:]_]*([^()]*)/()/g' | \
perl -ne 'if(/^(\s*)([^\s].*)$/){printf "<span style=\"color:#%02x0000\"\>%s%s</span>\n", length($1)*9,$1,$2}'
]]]
[[[ Further ugly:
indent -kr -l1000 -nut < nestmania.c | \
grep '^ *\(if\|else\|while\|for\|}\|{\)' | \
grep 'if\|else' | \
wc -l
divided by
indent -kr -l1000 -nut < nestmania.c | \
grep -v '^[{} ]*$\|^ */\?\*' | \
wc -l
multiplied by
indent -kr -l1000 -nut < nestmania.c | \
grep '^ *\(if\|else\|while\|for\|}\|{\)' | \
grep 'if\|else' | \
perl -ne 'if(/^(\s*)if/){$i++; $l += length($1)}END{print $l/$i/4, "\n"}'
]]]
Recent Entries
Categories
- Entries - 260
- Beer - 1
- Cycling - 2
- Food - 53
- Cooking - 26
- Hare - 5
- Soup - 1
- Eating - 5
- England - 5
- London - 4
- Rickmansworth - 1
- Produce - 14
- Ristretto - 8
- Health - 3
- Money - 2
- Random - 74
- Technology - 93
- Code - 22
- General - 46
- Security - 23
- Work - 2
- Wanderings - 32
- Australia - 2
- Barcelona - 2
- Belgium - 2
- England - 15
- Cambridge_Easter - 3
- Lakes - 9
- Finland - 4
- France - 1
- Germany - 1
- Ramble - 3
- Wales - 1




No Responses