Reputation: 87
While writing what should be a very simple program ( out of K&R C book ), I get some output which I do not understand. If I EOF
right away, nl_count
is correctly 0, but space_count
is always 32767 ( half of maximum int
range), and tab_count
is a large value ( usually very high or very low ).
When I initialize all variables to 0, then the program works correctly. What am I missing here?
10 int main(void)
11 {
12 int tab_count, space_count, nl_count;
13
14 //tab_count = space_count = nl_count = 0;
15
16 int c;
17 while( (c = getchar()) != EOF ){
18 if( c == '\t' )
19 tab_count++;
20 if( c == ' ' )
21 space_count++;
22 if( c == '\n' )
23 nl_count++;
24 }
25
26 printf("\n");
27 printf("TABS = %d\n", tab_count);
28 printf("SPACES = %d\n", space_count);
29 printf("NEWLINES = %d\n", nl_count);
30
31 return 0;
32 }
Inputs and Outputs:
Here is another input, which again correctly outputs 3 for newlines, but junk for tabs, and 32767 for spaces.
(space)(space)(space)\t\t\t\n\n\n
TABS = 441446448
SPACES = 32767
NEWLINES = 3
Upvotes: 1
Views: 81
Reputation: 134286
The problem here is, when you define automatic local variables, they are not initialized to any value implicitly. You have to initialize them explicitly. Otherwise, the content of those variables are garbage and indeterminate.
Reference: C11
, chapter §6.7.9, Initialization
If an object that has automatic storage duration is not initialized explicitly, its value is indeterminate.
Next, without a write (atleast, the initialization), if you try to use (read) the value, it invokes undefined behaviour.
Reference: C11
, Annex §J.2
The value of an object with automatic storage duration is used while it is indeterminate
Then, to answer
When I initialize all vars to 0, then the program works correctly
Yes, ofcourse, because, that way, there is no UB.
So, in your code, you have to change
int tab_count, space_count, nl_count;
to
int tab_count = 0;
int space_count = 0;
int nl_count = 0;
Upvotes: 2
Reputation: 227370
When I initialize all vars to 0, then the program works correctly. What am I missing here?
tab_count
, space_count
and nl_count;
are automatic storage variables. If you don't initialize them to 0
, they have a indeterminate values. Reading from them is technically undefined behaviour (UB). Since you're incrementing their value before initializing them, you are invoking UB. One manifestation of UB is to produce seemingly nonsensical values.
Upvotes: 5
Reputation: 2945
Only Extern and Static variables are initialized to 0 by default. All other variables have an indeterminate value, which is why you have to initialize them to 0 before using them.
Upvotes: 3
Reputation: 87944
I can't resist.
When I initialize all vars to 0, then the program works correctly. What am I missing here?
You are missing that you must initialise all the variables to zero.
Maybe what you are really missing is the fact that C programs that break the rules can have undefined/unspecified behaviour. This mean they can appear to work, or partially work, even though they are incorrect.
Upvotes: 2