This question already has answers here:
Why are these constructs using pre and post-increment undefined behavior?
(14 answers)
What is the difference between prefix and postfix operators?
(13 answers)
Closed 5 years ago.
I am trying to understand the basics of C programming and I'm kind of new to C, I am failing to understand why the output of my program is:
1 2
1 1
Quite alright, I understand the output from the first printf() but I do not seem to get the logic behind the second printf(). Why can't it display 1 2 as well?
#include <stdio.h>
int main()
{
int a = 1, b = 2;
printf("%d %d\n", a, b);
printf("%d %d\n", a, a++);
return 0;
}
a++ is post-incrementing a. That is, the value of a is copied before it is returned and then it is incremented.
As I mentioned in the comments, I get a different result to you, for the reason I explain below.
If you add printf("%d\n", a);, after your last call to printf() you'll see 2 because a has now been incremented.
If you want to see 1 2, you could pre-increment a (that is increment it and then use it), but you need to introduce a sequence point for this to be guaranteed to work because the order of evaluation of function arguments is unspecified by the standard and you want to use a twice:
printf("%d ", a);
printf("%d\n", ++a);
See it run!
The expression a++ evaluates to the current value of a and as a side effect increments a by 1. The expression ++a evaluates to the current value of a + 1 and as a side effect increments a by 1.
If you had written
a = 1;
printf("%d\n", a++);
you would get the output 1, because you're asking for the current value of a. Had you written
a = 1;
printf("%d\n", ++a);
you would get the output 2, because you're asking for the value of a + 1.
Now, what's important to remember (especially with ++a) is that the side effect of actually updating a doesn't have to happen immediately after the expression has been evaluated; it only has to happen before the next sequence point (which, in the case of a function call, is after all of the arguments have been evaluated).
Per the language definition, an object (such as the variable a) may have its value changed by the evaluation of an expression (a++ or ++a) at most once between sequence points, and the prior value shall be read only to determine the value to be stored.
The statement
printf("%d %d\n", a, a++);
violates the second part of that restriction, so the behavior of that statement is undefined. Your output could be any of 1 1, 1 2, a suffusion of yellow, etc.
Post Increment, increament after use
#include <stdio.h>
int main()
{
in a = 1, b = 2;
printf("%d %d\n", a, b); // 1 1
printf("%d %d\n", a, a++); // 1 1
printf("$d", a); // 2
return 0;
}
Following is pre-increment :
#include <stdio.h>
int main()
{
in a = 1, b = 2;
printf("%d %d\n", a, b); // 1 1
printf("%d %d\n", a, ++a); // Could Be "1 1" OR "1 2"... sequence is undefined here.
printf("$d", a); // 2
return 0;
}
Actually, ++x and x++ increment x the same way. The only difference is that ++x returns a reference to x and x++ returns the previous value as a temporary. The "incremented after it's been used" explanation is incorrect.
Related
This question already has answers here:
Why are these constructs using pre and post-increment undefined behavior?
(14 answers)
Order of operations for pre-increment and post-increment in a function argument? [duplicate]
(4 answers)
function parameter evaluation order
(5 answers)
Closed 4 months ago.
I'm new to C and I'm writting some simple stuff to get familiar. I just tried pre-increment on an array index and what I got was really not what I was expecting.
The code in question:
#include <stdio.h>
int main()
{
int array[5] = {1,2,3,4,5};
int i = 0;
printf("%d %d",array[i], array[++i]);
return 0;
}
which should display elements of array[0] and array[1], right?
But it doesn't, as the output is 2 2
What am I missing?
Here's the thing: You can't guarantee what order function arguments are evaluated in.
What this means is, in your printf call, there's no way to tell whether array[i] or array[++i] will be evaluated first. In your case it appears that array[++i] won, so what happens is that you end up printing array[1] twice.
That's not a good use of pre-increment.
If you want to look at array[i] and array[i+1], just do that:
printf("%d %d\n", array[i], array[i+1]);
Remember, i++ does not just take i's old value and add 1 to it. It takes i's old value, and adds 1 to it, and stores the new value back into i. When you were printing array[i] and array[i+1], did you really want to change the value of i?
If you did want to change the value of i — or, in any case, since that mention of array[i++] did change the value of i — you introduced undefined behavior. Once you've got an expression that's modifying the value of i, how do you know what array[i] will print? How do you know that array[i] won't end up using the new value of i? You probably assumed that things are evaluated from left to right, but it turns out that's not necessarily true. So weird, weird things can happen.
Here's an example that helps show how ++ works, and that's well-defined:
#include <stdio.h>
int main()
{
int array[5] = {1,2,3,4,5};
int i = 1;
array[i++] = 22;
array[++i] = 44;
for(i = 0; i < 5; i++)
printf("%d: %d\n", i, array[i]);
return 0;
}
Or, as you suggested in a comment, if you did want to modify i's value, perhaps to advance the variable i along the array, you sometimes have to take care to move the i++ into a separate statement. The simple rule is, if you're applying ++ or -- to a variable, you can only use that variable once in the same statement. So you can't have i++ + i++, since that has two i's in it and they're both modified. But you also can't have i + i++, or f(a[i], a[i++]), since those have a spot where you modify i, and a spot where you use i, and there's no way to know whether you use the old or the new value of i. (And, again, in C there's not a general left-to-right rule that helps you here.)
The following code prints a value of 9. Why? Here return(i++) will return a value of 11 and due to --i the value should be 10 itself, can anyone explain how this works?
#include<stdio.h>
main()
{
int i= fun(10);
printf("%d\n",--i);
}
int fun (int i)
{
return(i++);
}
There is a big difference between postfix and prefix versions of ++.
In the prefix version (i.e., ++i), the value of i is incremented, and the value of the expression is the new value of i.
In the postfix version (i.e., i++), the value of i is incremented, but the value of the expression is the original value of i.
Let's analyze the following code line by line:
int i = 10; // (1)
int j = ++i; // (2)
int k = i++; // (3)
i is set to 10 (easy).
Two things on this line:
i is incremented to 11.
The new value of i is copied into j. So j now equals 11.
Two things on this line as well:
i is incremented to 12.
The original value of i (which is 11) is copied into k. So k now equals 11.
So after running the code, i will be 12 but both j and k will be 11.
The same stuff holds for postfix and prefix versions of --.
Prefix:
int a=0;
int b=++a; // b=1,a=1
before assignment the value of will be incremented.
Postfix:
int a=0;
int b=a++; // a=1,b=0
first assign the value of 'a' to 'b' then increment the value of 'a'
The function returns before i is incremented because you are using a post-fix operator (++). At any rate, the increment of i is not global - only to respective function. If you had used a pre-fix operator, it would be 11 and then decremented to 10.
So you then return i as 10 and decrement it in the printf function, which shows 9 not 10 as you think.
In fact return (i++) will only return 10.
The ++ and -- operators can be placed before or after the variable, with different effects. If they are before, then they will be processed and returned and essentially treated just like (i-1) or (i+1), but if you place the ++ or -- after the i, then the return is essentailly
return i;
i + 1;
So it will return 10 and never increment it.
There are two examples illustrates difference
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , c++);
Here c has value 0 c increment by 1 then assign value 1 to a so value
of a = 1 and value of c = 1
next statement assiagn value of c = 1 to b then increment c by 1 so
value of b = 1 and value of c = 2
in printf statement we have c++ this mean that orginal value of c
which is 2 will printed then increment c by 1 so printf statement
will print 1 1 2 and value of c now is 3
you can use http://pythontutor.com/c.html
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , ++c);
Here in printf statement ++c will increment value of c by 1 first then
assign new value 3 to c so printf statement will print 1 1 3
The postfix increment ++ does not increase the value of its operand until after it has been evaluated. The value of i++ is i.
The prefix decrement increases the value of its operand before it has been evaluated. The value of --i is i - 1.
Prefix increment/decrement change the value before the expression is evaluated. Postfix increment/decrement change the value after.
So, in your case, fun(10) returns 10, and printing --i prints i - 1, which is 9.
i++ is post increment. The increment takes place after the value is returned.
First, note that the function parameter named i and the variable named i in main() are two different variables. I think that doesn't matter that much to the present discussion, but it's important to know.
Second, you use the postincrement operator in fun(). That means the result of the expression is the value before i is incremented; the final value 11 of i is simply discarded, and the function returns 10. The variable i back in main, being a different variable, is assigned the value 10, which you then decrement to get 9.
Explanation:
Step 1: int fun(int); Here we declare the prototype of the function fun().
Step 2: int i = fun(10); The variable i is declared as an integer type and the result of the fun(10) will be stored in the variable i.
Step 3: int fun(int i){ return (i++); } Inside the fun() we are returning a value return(i++). It returns 10. because i++ is the post-increement operator.
Step 4: Then the control back to the main function and the value 10 is assigned to variable i.
Step 5: printf("%d\n", --i); Here --i denoted pre-increement. Hence it prints the value 9.
Let's keep this as simple as possible.
let i = 1
console.log('A', i) // 1
console.log('B', ++i) // 2
console.log('C', i++) // 2
console.log('D', i) // 3
A) Prints the value of I.
B) First i is incremented then the console.log is run with i as it's the new value.
C) Console.log is run with i at its current value, then i will get incremented.
D) Prints the value of i.
In short, if you use the pre-shorthand i.e(++i) I will get updated before the line is executed. If you use the post-shorthand i.e(i++) the current line will run as if I had not been updated yet then i get increased so the next time your interpreter comes across i it will have been increased.
It has to do with the way the post-increment operator works. It returns the value of i and then increments the value.
Actually what happens is when you use postfix i.e. i++, the initial value of i is used for returning rather than the incremented one. After this the value of i is increased by 1. And this happens with any statement that uses i++, i.e. first initial value of i is used in the expression and then it is incremented.
And the exact opposite happens in prefix. If you would have returned ++i, then the incremented value i.e. 11 is returned, which is because adding 1 is performed first and then it is returned.
fun(10) returns 10. If you want it to return 11 then you need to use ++i as opposed to i++.
int fun(int i)
{
return ++i;
}
The following code prints a value of 9. Why? Here return(i++) will return a value of 11 and due to --i the value should be 10 itself, can anyone explain how this works?
#include<stdio.h>
main()
{
int i= fun(10);
printf("%d\n",--i);
}
int fun (int i)
{
return(i++);
}
There is a big difference between postfix and prefix versions of ++.
In the prefix version (i.e., ++i), the value of i is incremented, and the value of the expression is the new value of i.
In the postfix version (i.e., i++), the value of i is incremented, but the value of the expression is the original value of i.
Let's analyze the following code line by line:
int i = 10; // (1)
int j = ++i; // (2)
int k = i++; // (3)
i is set to 10 (easy).
Two things on this line:
i is incremented to 11.
The new value of i is copied into j. So j now equals 11.
Two things on this line as well:
i is incremented to 12.
The original value of i (which is 11) is copied into k. So k now equals 11.
So after running the code, i will be 12 but both j and k will be 11.
The same stuff holds for postfix and prefix versions of --.
Prefix:
int a=0;
int b=++a; // b=1,a=1
before assignment the value of will be incremented.
Postfix:
int a=0;
int b=a++; // a=1,b=0
first assign the value of 'a' to 'b' then increment the value of 'a'
The function returns before i is incremented because you are using a post-fix operator (++). At any rate, the increment of i is not global - only to respective function. If you had used a pre-fix operator, it would be 11 and then decremented to 10.
So you then return i as 10 and decrement it in the printf function, which shows 9 not 10 as you think.
In fact return (i++) will only return 10.
The ++ and -- operators can be placed before or after the variable, with different effects. If they are before, then they will be processed and returned and essentially treated just like (i-1) or (i+1), but if you place the ++ or -- after the i, then the return is essentailly
return i;
i + 1;
So it will return 10 and never increment it.
There are two examples illustrates difference
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , c++);
Here c has value 0 c increment by 1 then assign value 1 to a so value
of a = 1 and value of c = 1
next statement assiagn value of c = 1 to b then increment c by 1 so
value of b = 1 and value of c = 2
in printf statement we have c++ this mean that orginal value of c
which is 2 will printed then increment c by 1 so printf statement
will print 1 1 2 and value of c now is 3
you can use http://pythontutor.com/c.html
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , ++c);
Here in printf statement ++c will increment value of c by 1 first then
assign new value 3 to c so printf statement will print 1 1 3
The postfix increment ++ does not increase the value of its operand until after it has been evaluated. The value of i++ is i.
The prefix decrement increases the value of its operand before it has been evaluated. The value of --i is i - 1.
Prefix increment/decrement change the value before the expression is evaluated. Postfix increment/decrement change the value after.
So, in your case, fun(10) returns 10, and printing --i prints i - 1, which is 9.
i++ is post increment. The increment takes place after the value is returned.
First, note that the function parameter named i and the variable named i in main() are two different variables. I think that doesn't matter that much to the present discussion, but it's important to know.
Second, you use the postincrement operator in fun(). That means the result of the expression is the value before i is incremented; the final value 11 of i is simply discarded, and the function returns 10. The variable i back in main, being a different variable, is assigned the value 10, which you then decrement to get 9.
Explanation:
Step 1: int fun(int); Here we declare the prototype of the function fun().
Step 2: int i = fun(10); The variable i is declared as an integer type and the result of the fun(10) will be stored in the variable i.
Step 3: int fun(int i){ return (i++); } Inside the fun() we are returning a value return(i++). It returns 10. because i++ is the post-increement operator.
Step 4: Then the control back to the main function and the value 10 is assigned to variable i.
Step 5: printf("%d\n", --i); Here --i denoted pre-increement. Hence it prints the value 9.
Let's keep this as simple as possible.
let i = 1
console.log('A', i) // 1
console.log('B', ++i) // 2
console.log('C', i++) // 2
console.log('D', i) // 3
A) Prints the value of I.
B) First i is incremented then the console.log is run with i as it's the new value.
C) Console.log is run with i at its current value, then i will get incremented.
D) Prints the value of i.
In short, if you use the pre-shorthand i.e(++i) I will get updated before the line is executed. If you use the post-shorthand i.e(i++) the current line will run as if I had not been updated yet then i get increased so the next time your interpreter comes across i it will have been increased.
It has to do with the way the post-increment operator works. It returns the value of i and then increments the value.
Actually what happens is when you use postfix i.e. i++, the initial value of i is used for returning rather than the incremented one. After this the value of i is increased by 1. And this happens with any statement that uses i++, i.e. first initial value of i is used in the expression and then it is incremented.
And the exact opposite happens in prefix. If you would have returned ++i, then the incremented value i.e. 11 is returned, which is because adding 1 is performed first and then it is returned.
fun(10) returns 10. If you want it to return 11 then you need to use ++i as opposed to i++.
int fun(int i)
{
return ++i;
}
This question already has answers here:
subexpressions evaluation order
(2 answers)
Closed 5 years ago.
I have tried the following code and got confused:
#include <stdio.h>
int m=3;
int f(void)
{
m--;
return m;
}
int main()
{
m=f()+m; //as + operator is executed from left to right, it is okay that m=2+2
printf("%d\n", m); //m=4, as expected
m=m+f(); //as + operator is executed from left to right, it should be like m=4+3
printf("%d\n", m); //but m=6
m+= f();
printf("%d\n", m);
return 0;
}
plus (+) operator is commutative, but here it seemed that the order of the summands matters!!! (according to the rule of associativity)
Why m is equal to 6 after the execution of m=m+f();?
It looks like the function call will always get preference!!!!
I am not sure whether it's an undefined behavior. m=m+m-- is an undefined behavior, as far as I know, but here the decrement task has been performed in an indirect manner- by a function.
In the question "subexpressions evaluation order", the answer was that "each of func1 and func2 can, if desired, interact with some shared data without having that data change under it in an unexpected way", but here the value of m has been changed by the function f.
I tried this code later and found another interesting thing. The function evaluation precedence is not the matter here- as this shows
#include <stdio.h>
int m;
int f()
{
m--;
return m;
}
int main()
{
m=4;
int x;
x=m+f()+f(); //if f() is evaluated first, then it should be like m=3+2+2
printf("%d\n",x); // but m=8
return 0;
}
m=m+f(); //as + operator is executed from left to right, it should be like m=4+3
printf("%d\n", m); //but m=6
This is correct because function call has highest precedence over + operator.
You can have a look at tbis
I hope this would help you.
The following code prints a value of 9. Why? Here return(i++) will return a value of 11 and due to --i the value should be 10 itself, can anyone explain how this works?
#include<stdio.h>
main()
{
int i= fun(10);
printf("%d\n",--i);
}
int fun (int i)
{
return(i++);
}
There is a big difference between postfix and prefix versions of ++.
In the prefix version (i.e., ++i), the value of i is incremented, and the value of the expression is the new value of i.
In the postfix version (i.e., i++), the value of i is incremented, but the value of the expression is the original value of i.
Let's analyze the following code line by line:
int i = 10; // (1)
int j = ++i; // (2)
int k = i++; // (3)
i is set to 10 (easy).
Two things on this line:
i is incremented to 11.
The new value of i is copied into j. So j now equals 11.
Two things on this line as well:
i is incremented to 12.
The original value of i (which is 11) is copied into k. So k now equals 11.
So after running the code, i will be 12 but both j and k will be 11.
The same stuff holds for postfix and prefix versions of --.
Prefix:
int a=0;
int b=++a; // b=1,a=1
before assignment the value of will be incremented.
Postfix:
int a=0;
int b=a++; // a=1,b=0
first assign the value of 'a' to 'b' then increment the value of 'a'
The function returns before i is incremented because you are using a post-fix operator (++). At any rate, the increment of i is not global - only to respective function. If you had used a pre-fix operator, it would be 11 and then decremented to 10.
So you then return i as 10 and decrement it in the printf function, which shows 9 not 10 as you think.
In fact return (i++) will only return 10.
The ++ and -- operators can be placed before or after the variable, with different effects. If they are before, then they will be processed and returned and essentially treated just like (i-1) or (i+1), but if you place the ++ or -- after the i, then the return is essentailly
return i;
i + 1;
So it will return 10 and never increment it.
There are two examples illustrates difference
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , c++);
Here c has value 0 c increment by 1 then assign value 1 to a so value
of a = 1 and value of c = 1
next statement assiagn value of c = 1 to b then increment c by 1 so
value of b = 1 and value of c = 2
in printf statement we have c++ this mean that orginal value of c
which is 2 will printed then increment c by 1 so printf statement
will print 1 1 2 and value of c now is 3
you can use http://pythontutor.com/c.html
int a , b , c = 0 ;
a = ++c ;
b = c++ ;
printf (" %d %d %d " , a , b , ++c);
Here in printf statement ++c will increment value of c by 1 first then
assign new value 3 to c so printf statement will print 1 1 3
The postfix increment ++ does not increase the value of its operand until after it has been evaluated. The value of i++ is i.
The prefix decrement increases the value of its operand before it has been evaluated. The value of --i is i - 1.
Prefix increment/decrement change the value before the expression is evaluated. Postfix increment/decrement change the value after.
So, in your case, fun(10) returns 10, and printing --i prints i - 1, which is 9.
i++ is post increment. The increment takes place after the value is returned.
First, note that the function parameter named i and the variable named i in main() are two different variables. I think that doesn't matter that much to the present discussion, but it's important to know.
Second, you use the postincrement operator in fun(). That means the result of the expression is the value before i is incremented; the final value 11 of i is simply discarded, and the function returns 10. The variable i back in main, being a different variable, is assigned the value 10, which you then decrement to get 9.
Explanation:
Step 1: int fun(int); Here we declare the prototype of the function fun().
Step 2: int i = fun(10); The variable i is declared as an integer type and the result of the fun(10) will be stored in the variable i.
Step 3: int fun(int i){ return (i++); } Inside the fun() we are returning a value return(i++). It returns 10. because i++ is the post-increement operator.
Step 4: Then the control back to the main function and the value 10 is assigned to variable i.
Step 5: printf("%d\n", --i); Here --i denoted pre-increement. Hence it prints the value 9.
Let's keep this as simple as possible.
let i = 1
console.log('A', i) // 1
console.log('B', ++i) // 2
console.log('C', i++) // 2
console.log('D', i) // 3
A) Prints the value of I.
B) First i is incremented then the console.log is run with i as it's the new value.
C) Console.log is run with i at its current value, then i will get incremented.
D) Prints the value of i.
In short, if you use the pre-shorthand i.e(++i) I will get updated before the line is executed. If you use the post-shorthand i.e(i++) the current line will run as if I had not been updated yet then i get increased so the next time your interpreter comes across i it will have been increased.
It has to do with the way the post-increment operator works. It returns the value of i and then increments the value.
Actually what happens is when you use postfix i.e. i++, the initial value of i is used for returning rather than the incremented one. After this the value of i is increased by 1. And this happens with any statement that uses i++, i.e. first initial value of i is used in the expression and then it is incremented.
And the exact opposite happens in prefix. If you would have returned ++i, then the incremented value i.e. 11 is returned, which is because adding 1 is performed first and then it is returned.
fun(10) returns 10. If you want it to return 11 then you need to use ++i as opposed to i++.
int fun(int i)
{
return ++i;
}