views:

594

answers:

4

Example code:

    int a[] = new double[]{0, 1, 2, 3};
    int result = 0;
    for (int i : a)
        result += i;

Is the loop guaranteed to iterate across a[0], a[1], a[2], a[3] in that order? I strongly believe the answer is yes, but this page seems to not unambiguously state order.

Got a solid reference?

+11  A: 

According to the JLS, The enhanced for statement, your for-loop is equivalent to

int[] array = a;
for (int index = 0; index < a.length; index++) {
    int i = array[index];
    result += i;
}

"where array and index are compiler-generated identifiers that are distinct from any other identifiers (compiler-generated or otherwise) that are in scope at the point where the enhanced for statement occurs." (slightly paraphrasing the variable names here).

So yes: the order is absolutely guaranteed.

Joachim Sauer
Thanks! s/enchanced/enhanced/ above.
dfrankow
I think that second line should be:for (int index = 0; index < a.length; index++) {Perils of using "i" for something that isn't an index.
@cygil: of course, thanks. I was trying to re-use the variable names from the example code and promptly missed something.
Joachim Sauer
A: 

I did not find anything in the page you've referenced that would imply out-of-order iteration. Can you post the specific quote?

In any case, I find that this code:

public static void main( String args[] ) {
 double a[] = new double[] { 0, 1, 2, 3 };
 int result = 0;
 for ( double i : a ) {
  result += i;
 }

decompiles to old-style looping:

 public static void main(String args[])
    {
        double a[] = {
            0.0D, 1.0D, 2D, 3D
        };
        int result = 0;
        double ad[];
        int k = (ad = a).length;
        for(int j = 0; j < k; j++)
        {
            double i = ad[j];
            result = (int)((double)result + i);
        }
    }

Of course, that's not the same as a guarantee, but at the very least out-of-order iteration over an array would be very weird and would seem to go against obvious common-sense implementation.

Steve B.
It could be faster to split the elements and thread the loop. Some compilers already unroll and vectorize loops doing math. That is out of order. Threads could be the next thing.
Zan Lynx
+3  A: 

See section 14.14.2 of the Java Language Specification, 3rd edition.

If the type of Expression is a subtype of Iterable, then let I be the type of the expression Expression.iterator(). The enhanced for statement is equivalent to a basic for statement of the form:

for (I #i = Expression.iterator(); #i.hasNext(); ) {
        VariableModifiersopt Type Identifier = #i.next();
   Statement
}

Where #i is a compiler-generated identifier that is distinct from any other identifiers (compiler-generated or otherwise) that are in scope (§6.3) at the point where the enhanced for statement occurs.

vladr
+2  A: 

It states in the JLS http://java.sun.com/docs/books/jls/third_edition/html/statements.html#14.14.2

That

for ( VariableModifiersopt Type Identifier: Expression) Statement

is equivalent to

T[] a = Expression;
L1: L2: ... Lm:
for (int i = 0; i < a.length; i++) {
        VariableModifiersopt Type Identifier = a[i];
        Statement
}
Peter Lawrey