高速化のために,いくつかの基本的演算のベンチマークを取っていて驚くのはFirefox(Fx)での結果です.
function test() { var x; for (var i = 0; i < 1000000; i++) { x = 1 >> 1; // a // x = 1 >>> 1; // b // x = (-1) >> 1; // c // x = (-1) >>> 1; // d } }
a | b | c | d | |
IE | 110 | 110 | 110 | 110 |
Fx | 78 | 78 | 125 | 890 |
(注意) 1 >> 1をi >> 1や (-i) >> 1に変えてもほぼ同じ.
どれもほぼ一定のIEに比べてFxで(-1)>>>1がやたら遅いのはどうしてでしょうか.
if (INT_FITS_IN_JSVAL(i)) { \ v_ = INT_TO_JSVAL(i); \ } else { \ ok = js_NewDoubleValue(cx, (jsdouble)(i), &v_); \ if (!ok) \ goto out; \ }
となっています.
#INT_FITS_IN_JSVAL(j)は -230-1<=j<=230-1なら真のマクロ.
つまり,xの値がその範囲を超えるとdouble型に移行し,その値を保存するためにメモリ確保関数が呼び出されます.
これが他に比べて10倍以上遅い原因となっています.
同様に
var x = 0; for (var i = 0; i < 1000000; i++) { x += i; }
もFxはIEに比べて8倍近く遅くなります.SHA-1の演算では
230 - 1 < x < 2 32の整数は大量に出てくるわけですからこのペナルティは無視できません.
sha1.jsなどでは32bit整数値を二つの数値型変数に分けて入れることでそれに対応しました.