About foreach loops

bearophile bearophileHUGS at lycos.com
Tue Jun 14 19:20:45 PDT 2011


This post is about some characteristics of the D foreach that has nagged me for some time.

This is a little Python 2.6 program:


for i in xrange(10):
    i += 1
    print i,


Its output shows that you are allowed to modify the iteration variable (contents of the iteration name), but the iteration goes on with no change:
1 2 3 4 5 6 7 8 9 10


Similar code in D using foreach shows a different story:

import std.stdio;
void main() {
    foreach (i; 0 .. 10) {
        i += 1;
        write(i, " ");
    }
}

The output:
1 3 5 7 9 


In my opinion this is a bit bug-prone because in real code there is some risk of modifying the iteration variable "i" by mistake. (Note: here I am not talking about D for() loops. They are OK, their semantics is transparent enough. foreach() loops are less transparent and they *look* higher level than for() loops). I'd like the iteration variable to act as being a copy of the true loop variable as in Python. If this is a bit bad for foreach performance, then I'd like the compiler to forbid the mutation of the foreach iteration variable inside the foreach body. Is this even possible?


Currently you can't solve the problem adding a const(int) to the iteration variable:

import std.stdio;
void main() {
    foreach (const(int) i; 0 .. 10) { // line 3
        write(i, " ");
    }
}


DMD gives:
test.d(3): Error: variable test.main.i cannot modify const


This is a related but different thing:
http://d.puremagic.com/issues/show_bug.cgi?id=5255

Bye,
bearophile


More information about the Digitalmars-d mailing list