JavaScript Performance: Loops

JavaScript FAQ | Basic Syntax & General Questions  

Question: Are while(i--) loops faster than other kinds of JavaScript loops?
More generally: Are all kinds of empty loops equally fast – or are some faster than others?

Answer: Not all JavaScript loops are created equal: one iteration of an empty loop may take anywhere from a couple of CPU clock cycles to over 100 cycles. Which kind of loop is faster strongly depends on the browser running the script and, particularly, whether the browser's JavaScript engine uses JIT compilation or not. Here are the results of the relative performance measurements for several kinds of empty loops in MSIE 8.0, Firefox 3.6.17, Opera 11.10, Safari 5.0.3, Chrome 11.0.696.60, under Windows XP SP3, with a 2GHz CPU.

Overall performance: JIT is faster! The fastest overall was Chrome 11 (under 2 sec per billion iterations, or at most 4 CPU cycles per iteration); the slowest was IE8 (about 55 sec per billion iterations, or over 100 CPU cycles per iteration). This is not surprising: among all browsers we tested under Windows XP, the only one that does not use JavaScript JIT compilation is IE8. Internet Explorer 9 does support JIT but is not available on Windows XP. On a separate Windows 7 system, IE9 performance results are close to those of other JIT-enabled browsers.

Relative performance of different loops. The relative performance is shown as percentage of the traditional for loop run time in the same browser. (That is, 100% represents the run time of  for(var i=0;i<n;i++){} in the particular browser.) The only non-JIT browser was IE8 (left column) – and, indeed, the while(i--) and do{}while(i--) loops were faster than others in IE8. This is no longer the case in browsers with JavaScript JIT compilation; the results differ from browser to browser.

                                 MSIE8  FF3.6  Opera  Safari  Chrome

for (var i=0; i < n; i++) {}     100.0  100.0  100.0  100.0   100.0
for (var i=n; i > 0; i--) {}      92.5   99.5  101.5   85.8   101.0
for (var i=n; i >=0; i--) {}      92.5  100.6  101.4   85.7   102.2
for (var i=n; i-- != 0; ) {}      74.6   99.7  181.5  183.0   146.1
for (var i=n; i--; ) {}           53.1   99.3  189.1  113.4   145.9

var i=n; while (i < n) {i++;}     96.8  100.2  100.9   99.6   100.0
var i=0; while (i > 0) {i--;}     93.5  100.1  101.0   70.7   101.2
var i=n; while (i--) {}           53.1   99.0  190.1  114.1   146.8

var i=n; do {i++;} while (i < n)  90.2  100.0  101.6   99.5   147.5
var i=0; do {i--;} while (i > 0)  84.5  100.2  101.4   86.4   146.7
var i=n; do {} while (i--)        45.5   91.1  188.3  114.2   146.5
All measurements are for 1 billion iterations (which takes more than 1 second but less than 1 minute in each browser tested). The Windows XP SP3 system used was a Dell Inspiron 1520 with Intel Core 2 Duo CPU 2GHz, 4GB RAM. In all tested browsers except IE8, one iteration takes 10 CPU clock cycles or less.

Below you can measure the performance of typical loop statements in your browser (). Click the Run button to measure the execution time of the function call in the left column. (For more accurate results, use the average execution time over ten or more runs.)


 
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %
  Average: %

The JavaScript source code of the functions used in this test is as follows:

function for_loop_up(n)      { for (var i=0; i < n; i++) {} return i; }

function for_loop_down(n)    { for (var i=n; i > 0; i--) {} return i; }

function for_loop_ge(n)      { for (var i=n; i >=0; i--) {} return i; }

function for_loop_nocmp(n)   { for (var i=n; i--; ) {} return i; }

function while_loop_up(n)    { var i=0; while (i < n) {i++;} return i; }

function while_loop_down(n)  { var i=n; while (i > 0) {i--;} return i; }

function while_loop_nocmp(n) { var i=n; while (i--) {} return i}

function do_while_up(n)      { var i=0; do {i++;} while (i < n); return i; }

function do_while_down(n)    { var i=n; do {i--;} while (i > 0); return i; }

function do_while_nocmp(n)   { var i=n; do {} while (i--); return i; }

function ugly_for_loop(n)    { for (var i=n; i-- != 0; ) {} return i; }

*To measure performance in MSIE8, disable the slow script warnings, otherwise the warnings might interfere with the test runs.

Copyright © 1999-2011, JavaScripter.net.