I was trying something else but suddenly stuck with this infinite loop . Please suggest an answer with explanation that what's going on here in the below for loop
#include<stdio.h>
int main()
{
int x=0;
int i;
int array[5];
for(i=0;i<=5;i++)
{
array[i]=x;
printf("#%d value set in index %d\n",x,i);
}
return 0;
}
When I remove =
sign in the condition of for
loop It works fine.
But when I put this it goes to infinite loop , Why? Accessing extra element (more than its limit) in array is undefined behaviour or what ? Any help will appreciated. Thanks in advance.
~
Your for loop should go from 0 to 4 as your array has 5 elements
You are trying to store 6 int values in an array of size 5, which is illegal.
So when you try to write at the 6th position of the array, you are writing into the variable
i
with the value ofx
(which is 0). Now in your next iteration sincei
is 0, it is less than the condition specified in thefor
loop. This causes your loop to run all over again and again!Why you're going into an infinite loop, in this specific case, is actually pretty easy to understand, take a look at the addresses on your stack:
The result of this
printf()
will show you the addresses of your variables and the start and end of the array:So in order, your stack looks like:
Now your loop is writing 0-5 (6 elements), there are only 5 elements in your array so writing to the 6th actually overwrites the next thing on the stack which is
i
in this case. That makes this line:The same as writing this:
That will store 0 (in your case) to i, and restart the loop, so you're going to see it loop forever and print "0 stored to index 0", then "index 1", 2, 3, 4 then restart again when you set
i=x;
Undefined behavior happens when
i==5
.array
has valid indexes0..4
- arrays in C are 0-based.If you replace
<=
with<
, you iterate through valid indexes.Yes.
You're writing 6 ints to an array with space for 5. The 6th write is outside the bounds of the array so its effect is unpredictable. In your case, its writing to the next
sizeof(int)
bytes of stack. This is the memory used fori
, the loop counter, which gets reset to 0.As you say in your question, the fix for this is to replace the
<=
exit condition of your for loop with<
.To avoid causing errors like this as easily, here's two good rules for writing
for
loops over actual (local) arrays:<
, always. Never<=
.sizeof array / sizeof *array
. Note the asterisk in the second term.So, this loop should have been written:
and then you would have been safe.
Note that this only works for "real" arrays that have a size visible to
sizeof
, if you've let the array "collapse" into a pointer it won't work.Also note that
sizeof
is not a function, so no()
s are necessary around its argument in cases like these.