Hi,

I confirm your results. I didn't think there could be a difference using
foreach constructs...

Cedric


Steven A Rowe wrote:
> 
> On 04/04/2008 at 4:40 AM, Toke Eskildsen wrote:
>> On Wed, 2008-04-02 at 09:30 -0400, Mark Miller wrote:
>> > > - replacement of indexed for loops with for each constructs
>> > 
>> > Is this always the best idea? Doesn't the for loop construct make an
>> > iterator, which can be much slower than an indexed for loop?
>> 
>> Only in the case of iterations over collections. For arrays, the foreach
>> is syntactic sugar for indexed for-loop.
>> http://java.sun.com/docs/books/jls/third_edition/html/statements.html#14.14.2
> 
> I don't think this is actually true.  The text at the above-linked page
> simply says that for-each over an array "means the same as" an indexed
> loop over the same array.  "Syntactic sugar", OTOH, implies that the
> resulting opcode is exactly the same.  When I look at the byte code (using
> javap) for the comparison test I include below, I can see that the indexed
> and for-each loops do not generate the same byte code.
> 
> I constructed a simple program to compare the runtime length of the two
> loop control mechanisms, while varying the size of the array.  The test
> program takes command line parameters to control which loop control
> mechanism to use, the size of the array (#elems), and the number of times
> to execute the loop (#iters).  I used a Bash shell script to invoke the
> test program.
> 
> Summary of the results: over int[] arrays, indexed loops are faster on
> arrays with fewer than about a million elements.  The fewer the elements,
> the faster indexed loops are relative to for-each loops.  This could be
> explained by a higher one-time setup cost for the for-each loop - above a
> certain array size, the for-each setup cost is lost in the noise.  It
> should be noted, however, that this one-time setup cost is quite small,
> and might be worth the increased code clarity.
> 
> Here are the results for three different platforms:
> 
>   - Best of five iterations for each combination
>   - All using the -server JVM option
>   - Holding constant #iters * #elems = 10^10
>   - Rounding the reported real time to the nearest tenth of a second
>   - "% Slower" = 100 * ((For-each - Indexed) / Indexed)
> 
> Platform #1: Windows XP SP2; Intel Core 2 duo [EMAIL PROTECTED]; Java 1.5.0_13
> 
> #iters  #elems  For-each  Indexed  % Slower
> ------  ------  --------  -------  --------
>   10^9    10^1     22.3s    13.8s       62%
>   10^8    10^2     16.0s    13.6s       18%
>   10^6    10^4     14.8s    13.0s       14%
>   10^4    10^6     12.9s    12.9s        0%
>   10^3    10^7     13.4s    13.3s        1%
> 
> Platform #2: Debian Linux, 2.6.21.7 kernel; Intel Xeon [EMAIL PROTECTED]; Java
> 1.5.0_14
> 
> #iters  #elems  For-each  Indexed  % Slower
> ------  ------  --------  -------  --------
>   10^9    10^1     33.6s    14.2s      137%
>   10^8    10^2     20.4s    13.9s       47%
>   10^6    10^4     19.0s    12.7s       50%
>   10^4    10^6     12.7s    12.8s       -1%
>   10^3    10^7     13.2s    13.2s        0%
> 
> Platform #3: Debian Linux, 2.6.21.7 kernel; Intel Xeon [EMAIL PROTECTED]; Java
> 1.5.0_10
> 
> #iters  #elems  For-each  Indexed  % Slower
> ------  ------  --------  -------  --------
>   10^9    10^1    102.7s    73.6s       40%    
>   10^8    10^2    107.8s    60.0s       80%
>   10^6    10^4    105.2s    58.6s       80%
>   10^4    10^6     58.8s    53.0s       11%
>   10^3    10^7     60.0s    54.1s       11%
> 
> 
> ----- ForEachTest.java follows -----
> 
> import java.util.Date;
> import java.util.Random;
> 
> /**
>  * This is meant to be called from a shell script that varies the loop
> style,
>  * the number of iterations over the loop, and the number of elements in
> the
>  * array over which the loop iterates, e.g.:
>  * 
>  *     cmd="java -server -cp . ForEachTest"
>  *     for elems in 10 100 10000 1000000 10000000 ; do
>  *         iters=$((10000000000/${elems}))
>  *         for run in 1 2 3 4 5 ; do
>  *             time $cmd --indexed --arraysize $elems --iterations $iters
>  *             time $cmd --foreach --arraysize $elems --iterations $iters
>  *         done
>  *     done
>  *
>  */
> public class ForEachTest {
>   static String NL = System.getProperty("line.separator");
>   static String usage
>     = "Usage: java -server -cp . ForEachTest [ --indexed | --foreach ]"
>       + NL + "\t--iterations <num-iterations>  --arraysize <array-size>";
>     
>   public static void main(String[] args) {
>     boolean useIndexedLoop = false;
>     int size = 0;
>     int iterations = 0;
>     try {
>       for (int argnum = 0 ; argnum < args.length ; ++argnum) {
>         if (args[argnum].equals("--indexed")) {
>           useIndexedLoop = true;
>         } else if (args[argnum].equals("--foreach")) {
>           useIndexedLoop = false;
>         } else if (args[argnum].equals("--iterations")) {
>           iterations = Integer.parseInt(args[++argnum]);
>         } else if (args[argnum].equals("--arraysize")) {
>           size = Integer.parseInt(args[++argnum]);
>         } else {
>           throw new Exception("Unknown cmdline parameter '"
>                               + args[argnum] + "'.");
>         }
>       }
>     } catch (Exception e) {
>       System.err.println("Error parsing command line: " + e + NL);
>       System.err.println(usage);
>       System.exit(1);
>     }
> 
>     // Initial the array with random integers
>     int[] array = new int[size];
>     Random random = new Random();
>     for (int i = 0 ; i < size ; ++i) {
>       array[i] = random.nextInt();
>     }
>     
>     int k = 0;
>     if (useIndexedLoop) {
>       System.out.println("Indexed : " + iterations + " iterations : "
>                          + size + " elements");
>       for (int m = 0 ; m < iterations ; ++m) {
>         for (int j = 0 ; j < size ; ++j) {
>           k = array[j];
>         }
>       }
>     } else { // useIndexedLoop = false
>       System.out.println("For-each : " + iterations + " iterations : "
>                          + size + " elements");
>       for (int m = 0 ; m < iterations ; ++m) {
>         for (int j : array) {
>           k = j;
>         }
>       }
>     }
>     k = 0;
>   }
> }
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: [EMAIL PROTECTED]
> For additional commands, e-mail: [EMAIL PROTECTED]
> 
> 
> 

-- 
View this message in context: 
http://www.nabble.com/-jira--Created%3A-%28LUCENE-1257%29-Port-to-Java5-tp16445478p16587806.html
Sent from the Lucene - Java Developer mailing list archive at Nabble.com.


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to