Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

c++ iterator stuck at first value

Tags:

c++

I'm learning c++ and I've run into some behaviour that I can't explain. The two pieces of code below provide different results, while I would expect them to be equivalent:

success = true;
vector<instruction>::const_iterator i;
for (i = instructions.begin(); i != instructions.end(); ++i) {
    bool up = update(*i);
    success = success && up;        
}

and

success = true;
vector<instruction>::const_iterator i;
for (i = instructions.begin(); i != instructions.end(); ++i) {
    success = success && update(*i);        
}

I have the impression that the second version always takes the initial value of the iterator. Could someone explain me the reason?

like image 613
splinter123 Avatar asked Dec 16 '15 08:12

splinter123


2 Answers

The two pieces of code are not equivalent.

The first one always calls update, while the second one will not. The reason is that && does something called short-circuit boolean evaluation. If success is false, the second half of the expression is not evaluated.

Note that you did not post what update is or what is returned. Therefore we can only assume what may be able to be returned from update, which is either going to be true or false.

If you wanted update to always be called, it should be placed first in the && expression.

like image 51
PaulMcKenzie Avatar answered Oct 17 '22 15:10

PaulMcKenzie


The operator && will not evaluate the right hand side if the result is computable with just the left hand side value. We call this short-circuiting.

Once success is false, update(*i) will no longer be called.

Aside from your first block of code (which always calls update(*i)), one fix is to use the operator & instead which always evaluates both arguments. Another fix is to write

success = update(*i) && success;

But that's vulnerable to recalcitrant refactoring. Better still, use

success &= update(*i);

But be aware of this comment by @Angew:

Using &= in a boolean context is dangerous. What if update now (or after a future refactoring) returns an int with the semantics "non-zero for true" (cf. isdigit and friends)? Remember that bool(true & 2) is false.

like image 4
Bathsheba Avatar answered Oct 17 '22 14:10

Bathsheba