My answer.
It's mostly redundant with the previous (better) answer by @Joey. It got my vote.
It's still got a twist of it's own, so here goes.
It's an annotated revision. It's still O(n) -- don't see how it could NOT be.
It's more idiomatic and less redundant. It's not compiled or tested.
It doesn't raise the question "What does (sum>n<<2)
have to do with anything?"
It's a non-void return type. It describes the type of the result. It doesn't mess with some global like output1 that you would have to remember to define somewhere.
unsigned int GetCount(char* input2)
{
unsigned count = 0;
int sum = 0;
It's a comment. It explains things that aren't at all apparent like, just for example, what (sum>n<<2)
might have to do with anything.
int saw_a_digit = 0; /* only consider counting (again) after seeing a digit */
It's a loop. It's better than a goto. It's a for loop. It works well when incrementing a pointer once after each time through the loop.
It's got a test for null that only needs to be in this one place.
It's got an increment that doesn't need to dereference the pointer with '*'.
for(; *input2; input2++)
{
if(isdigit(*input2))
{
It's a minor optimization over summing digits. It doesn't require counting digits or calculating an average or calculating anything even remotely like (sum>n<<2)
. Why would it? It's a little tricky, so there's another comment.
/* We don't need the digit, just how it relates to 5.
* Amounts > 5 gets canceled out by amounts < 5,
* 0s and 9s have more influence than 4s and 6s.
* '5' has no effect at all.
* This would take a very long string of digits mostly
* on on the same side of 5 to overflow sum. */
It's white space in a non-trivial statement.
It's readable.
sum += *input2-'5';
saw_a_digit = 1;
}
else if (saw_a_digit) // found end of digit string
{
if (sum >= 0) // low influence did not dominate
{
++count;
}
sum = 0;
saw_a_digit = 0;
}
}
}
It's an alternative that uses two smaller loops.
It avoids mode variables like saw_a_digit
.
It MAY be a little faster.
unsigned int GetCount(char* input2)
{
unsigned count=0;
int sum;
while (*input2)
{
for (;!isdigit(*input2);input2++) /* skip non-digits */
if (!*input2)
return count;
sum=0;
do {
/* We don't need the digit, just how it relates to 5.
* Amounts > 5 get canceled out by amounts < 5,
* 0s and 9s have more influence than 4s and 6s.
* '5' has no effect at all.
* This would take a very long string of digits mostly
* on on the same side of 5 to overflow sum. */
sum += *input2-'5';
} while (isdigit(*++input2));
if (sum>=0) // low influence did not dominate
{
++count;
}
}
return count;
}
n
passed into the function if the first thing you do is set it to zero? – Jonathan Leffler Jan 14 '12 at 18:04goto
: You are going to hear, again and again, that you should never usegoto
. Like any best practice, try to adhere to it, but take it with a grain of salt. Since C lacks exceptions and closures, and does not guarantee optimized tail recursion, there are legitimate uses forgoto
(e.g. jumping to cleanup code at the end of your function). However, it takes a lot of maturity to know whengoto
is a good idea. Take a look at this parser I wrote in C a couple years ago, and decide for yourself if it abusesgoto
. – Joey Adams Jan 15 '12 at 1:08