Incrementing in C++ - When to use x++ or ++x?

C++Post IncrementPre Increment

C++ Problem Overview


I'm currently learning C++ and I've learned about the incrementation a while ago. I know that you can use "++x" to make the incrementation before and "x++" to do it after.

Still, I really don't know when to use either of the two... I've never really used "++x" and things always worked fine so far - so, when should I use it?

Example: In a for loop, when is it preferable to use "++x"?

Also, could someone explain exactly how the different incrementations (or decrementations) work? I would really appreciate it.

C++ Solutions


Solution 1 - C++

It's not a question of preference, but of logic.

x++ increments the value of variable x after processing the current statement.

++x increments the value of variable x before processing the current statement.

So just decide on the logic you write.

x += ++i will increment i and add i+1 to x. x += i++ will add i to x, then increment i.

Solution 2 - C++

Scott Meyers tells you to prefer prefix except on those occasions where logic would dictate that postfix is appropriate.

"More Effective C++" item #6 - that's sufficient authority for me.

For those who don't own the book, here are the pertinent quotes. From page 32:

> From your days as a C programmer, you may recall that the prefix form of the increment operator is sometimes called "increment and fetch", while the postfix form is often known as "fetch and increment." The two phrases are important to remember, because they all but act as formal specifications...

And on page 34:

> If you're the kind who worries about efficiency, you probably broke into a sweat when you first saw the postfix increment function. That function has to create a temporary object for its return value and the implementation above also creates an explicit temporary object that has to be constructed and destructed. The prefix increment function has no such temporaries...

Solution 3 - C++

From cppreference when incrementing iterators:

> You should prefer pre-increment > operator (++iter) to post-increment > operator (iter++) if you are not going > to use the old value. Post-increment > is generally implemented as follows: >

   Iter operator++(int)   {
     Iter tmp(*this); // store the old value in a temporary object
     ++*this;         // call pre-increment
     return tmp;      // return the old value   }

> > Obviously, it's less efficient than > pre-increment.

Pre-increment does not generate the temporary object. This can make a significant difference if your object is expensive to create.

Solution 4 - C++

I just want to notice that the geneated code is offen the same if you use pre/post incrementation where the semantic (of pre/post) doesn't matter.

example:

pre.cpp:

#include <iostream>

int main()
{
  int i = 13;
  i++;
  for (; i < 42; i++)
    {
      std::cout << i << std::endl;
    }
}

post.cpp:

#include <iostream>

int main()
{

  int i = 13;
  ++i;
  for (; i < 42; ++i)
    {
      std::cout << i << std::endl;
    }
}

_

$> g++ -S pre.cpp
$> g++ -S post.cpp
$> diff pre.s post.s   
1c1
< 	.file	"pre.cpp"
---
> 	.file	"post.cpp"

Solution 5 - C++

The most important thing to keep in mind, imo, is that x++ needs to return the value before the increment actually took place -- therefore, it has to make a temporary copy of the object (pre increment). This is less effecient than ++x, which is incremented in-place and returned.

Another thing worth mentioning, though, is that most compilers will be able to optimize such unnecessary things away when possible, for instance both options will lead to same code here:

for (int i(0);i<10;++i)
for (int i(0);i<10;i++)

Solution 6 - C++

I agree with @BeowulfOF, though for clarity I would always advocate splitting the statements so that the logic is absolutely clear, i.e.:

i++;
x += i;

or

x += i;
i++;

So my answer is if you write clear code then this should rarely matter (and if it matters then your code is probably not clear enough).

Solution 7 - C++

If count{5};

If you use ++count it will be process beforethe statement

total = --count +6;

Total will be equal to 10

If you use count++ it will be process after the statement

total = count-- +6;

Total will be equal to 11

Solution 8 - C++

Just wanted to re-emphasize that ++x is expected to be faster than x++, (especially if x is an object of some arbitrary type), so unless required for logical reasons, ++x should be used.

Solution 9 - C++

>Postfix form of ++,-- operator follows the rule use-then-change , > >Prefix form (++x,--x) follows the rule change-then-use.

Example 1:

When multiple values are cascaded with << using cout then calculations(if any) take place from right-to-left but printing takes place from left-to-right e.g., (if val if initially 10)

 cout<< ++val<<" "<< val++<<" "<< val;

will result into

12    10    10 

Example 2:

In Turbo C++, if multiple occurrences of ++ or (in any form) are found in an expression, then firstly all prefix forms are computed then expression is evaluated and finally postfix forms are computed e.g.,

int a=10,b;
b=a++ + ++a + ++a + a;
cout<<b<<a<<endl;

It's output in Turbo C++ will be

48 13

Whereas it's output in modern day compiler will be (because they follow the rules strictly)

45 13
  • Note: Multiple use of increment/decrement operators on same variable in one expression is not recommended. The handling/results of such
    expressions vary from compiler to compiler.

Solution 10 - C++

You explained the difference correctly. It just depends on if you want x to increment before every run through a loop, or after that. It depends on your program logic, what is appropriate.

An important difference when dealing with STL-Iterators (which also implement these operators) is, that it++ creates a copy of the object the iterator points to, then increments, and then returns the copy. ++it on the other hand does the increment first and then returns a reference to the object the iterator now points to. This is mostly just relevant when every bit of performance counts or when you implement your own STL-iterator.

Edit: fixed the mixup of prefix and suffix notation

Solution 11 - C++

You asked for an example:

This (order is a std::vector) will crash for i == order.size()-1 on the order[i].size() access:

while(i++ < order.size() && order[i].size() > currLvl);

This will not crash at order[i].size(), as i will be incremented, checked and the loop will be exited:

while(++i < order.size() && order[i].size() > currLvl);

Solution 12 - C++

Understanding the language syntax is important when considering clarity of code. Consider copying a character string, for example with post-increment:

char a[256] = "Hello world!";
char b[256];
int i = 0;
do {
  b[i] = a[i];
} while (a[i++]);

We want the loop to execute through encountering the zero character (which tests false) at the end of the string. That requires testing the value pre-increment and also incrementing the index. But not necessarily in that order - a way to code this with the pre-increment would be:

int i = -1;
do {
  ++i;
  b[i] = a[i];
} while (a[i]);

It is a matter of taste which is clearer and if the machine has a handfull of registers both should have identical execution time, even if a[i] is a function that is expensive or has side-effects. A significant difference might be the exit value of the index.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionJesse EmondView Question on Stackoverflow
Solution 1 - C++Oliver FriedrichView Answer on Stackoverflow
Solution 2 - C++duffymoView Answer on Stackoverflow
Solution 3 - C++Phillip NganView Answer on Stackoverflow
Solution 4 - C++chubView Answer on Stackoverflow
Solution 5 - C++rmnView Answer on Stackoverflow
Solution 6 - C++BidsView Answer on Stackoverflow
Solution 7 - C++IsmaelView Answer on Stackoverflow
Solution 8 - C++Shailesh KumarView Answer on Stackoverflow
Solution 9 - C++Sunil DhillonView Answer on Stackoverflow
Solution 10 - C++Björn PollexView Answer on Stackoverflow
Solution 11 - C++immerhartView Answer on Stackoverflow
Solution 12 - C++shkeyserView Answer on Stackoverflow