Never seen before C++ for loop
I was converting a C++ algorithm to C#. I came across this for loop:
for (u = b.size(), v = b.back(); u--; v = p[v])
b[u] = v;
It gives no error in C++, but it does in C# (cannot convert int to bool). I really can't figure out this for loop, where is the condition?
Can someone please explain?
PS. Just to check, to adapt a VECTOR to a LIST does b.back() correspond to b[b.Count-1] ?
Solution 1:
The condition of the for
loop is in the middle - between the two semicolons ;
.
In C++ it is OK to put almost any expression as a condition: anything that evaluates to zero means false
; non-zero means true
.
In your case, the condition is u--
: when you convert to C#, simply add != 0
:
for (u = b.size(), v = b.back(); u-- != 0; v = p[v])
b[u] = v; // ^^^^ HERE
Solution 2:
Lots of accurate answers, but I think it's worth writing out the equivalent while loop.
for (u = b.size(), v = b.back(); u--; v = p[v])
b[u] = v;
Is equivalent to:
u = b.size();
v = b.back();
while(u--) {
b[u] = v;
v = p[v];
}
You might consider refactoring to the while() format as you translate to C#. In my opinion it is clearer, less of a trap for new programmers, and equally efficient.
As others have pointed out -- but to make my answer complete -- to make it work in C# you would need to change while(u--)
to while(u-- != 0)
.
... or while(u-- >0)
just in case u starts off negative. (OK, b.size()
will never be negative -- but consider a general case where perhaps something else initialised u).
Or, to make it even clearer:
u = b.size();
v = b.back();
while(u>0) {
u--;
b[u] = v;
v = p[v];
}
It's better to be clear than to be terse.
Solution 3:
The condition is u--;
, because it is in the second position of the for instruction.
If the value of u--;
is different from 0, it will be interpreted as true
(i.e., implicitly casted to the boolean value true
). If, instead, its value is 0, it will be casted to false
.
This is very bad code.
Update: I discussed the writing of "for" loops in this blog post. Its recommendations can be summarized in the following paragraphs:
A for loop is a practical, readable (once you get used to it) and terse construct, but you need to use it well. Because of its uncommon syntax, using it in a too imaginative way is not a good idea.
All parts of the for loop should be short and readable. Variable names should be chosen to make it easy to understand.
This example clearly violates these recomendations.