Reputation: 127
I have a question regarding how uninitialized variables work in C. If I declare a variable and then print it, the program should print a random value, however my program almost always outputs 0. If I try to declare a second variable, the program always outputs 16 as the new assigned value.
#include <stdio.h>
int main(){
int x,y,z,t;
printf("%d %d",x,y);
}
This program outputs 0 and 16, however if I add the following line of code: y--;
right after declaring the variables but before printing them, the program outputs x=15 and y =-1, totally different values from what I had before. Why does this happen? How does C handle uninitialized variables?
Upvotes: 0
Views: 604
Reputation: 48053
One way of answering this is that when you read that "uninitialized variables start out containing random values", in this context, those values 0, 16, 15, and -1 that you saw are "random".
Now, it's true, they're certainly not random in the way that, say, the roll of a dice is random. They seem to stay the same, then change for no seemingly sensible reason, like when you change some other part of your program.
But you obviously can't predict them. So you obviously can't use them, or depend on them in any way. They might as well be truly random.
Why do they have the specific values that they do? It's almost impossible to say. Whatever the reasons are, they tend not to be very interesting. Whatever the reasons are, they're usually not important to know, since in any sane program you're never going to be depending on those uninitialized values anyway.
It's kind of like asking, "I sawed three legs off my kitchen table. Everything fell to the floor and broke. Except one plate didn't break. Why didn't it break? Also there was an apple, and it rolled into the living room. I expected it would roll down the basement stairs. Why did it roll into the living room?" Most of the time, the answer is simply: "Don't saw legs off your table in the first place!"
The other part of your question had to do with the fact that your uninitialized variable y
seemed to start out containing the value 16, but when you added the statement y--
, the value went to -1. What's up with that?
And the answer is that we're talking about uninitialized variables and unpredictable behavior. When you fail to initialize a variable, meaning that your program has unpredictable behavior, what does not happen is that some oracle somewhere picks an initial value for your variable, and then arranges for everything else about your program to be predictable. No, what it means for your program to be unpredictable is that you can't predict it! If the unpredictable value seemed to be 16 yesterday, you cannot predict that subtracting 1 from it will give you 15 tomorrow.
(To continue my silly analogy, if you were to saw the legs off your kitchen table again tomorrow, you would not expect that you'd necessarily end up with exactly one unbroken plate again. And if you sawed the legs off in a different order, hoping for the table to fall at a different angle and direct the apple down the basement stairs like you expected, you probably wouldn't be too disappointed if it didn't work.)
If you really want to know what's going on, part of the answer is that local variables are typically stored on the stack, and they start out containing whatever "random" bit pattern was left in that location on the stack by whatever function last used that piece of the stack for its own variables. So anything that moves things around on the stack, that causes your uninitialized variable to occupy a different spot in the stack frame, or that causes the previous function to leave different garbage on the stack, will cause your uninitialized variable to start out holding a different "random" value. See this other answer for some more discussion on what happens when you try to use uninitialized stack-based variables.
See also xkcd 221.
Upvotes: 2
Reputation: 44340
According to the standard (draft N1570) the following applies:
6.2.4
The initial value of the object is indeterminate.
This is further described in
6.7.9
If an object that has automatic storage duration is not initialized explicitly, its value is indeterminate.
The definition of "indeterminate" says
3.19.2
indeterminate value
either an unspecified value or a trap representation
And finally
J.2 Undefined behavior
The behavior is undefined in the following circumstances:
...
The value of an object with automatic storage duration is used while it is indeterminate (6.2.4, 6.7.9, 6.8).
So all together: There is no way to know what value you get when reading an uninitialized variable and further it's not even sure that your program will continue to execute as it may be a trap.
Upvotes: 2