小数点以下第x位を四捨五入(2007/05/20修正)

1.255の小数点第3位を四捨五入することにより、1.26という値を期待したのですが、、

>>> (1.255).toFixed(2)
"1.25"
>>> Math.round(1.255 * 100) / 100
1.25

toFixedでも、小数点の位置変えてMath.round()使っても、予想した結果(1.26)にならない(浮動小数点の丸め誤差が出てしまっている)ので、浮動小数点での演算が行われないように文字列&整数で扱って「小数点以下第x位を四捨五入」ってのを実現する方法を考えてみました。

var digitRound = function(num, digit) {
  var isMinus = num < 0;
  var num = String(num);
  var sepIndex = num.indexOf('.');

  if (sepIndex != -1) {
    var before = num.substring(0, sepIndex);
    var after = num.substring(sepIndex + 1);

    if (after.length > digit) {
      after = after.substring(0, digit + 1);

      var tempNum = String(parseInt(before + after, 10) + ((!isMinus) ? 5 : -4));

      before = tempNum.substring(0, tempNum.length - after.length);
      tempNum = tempNum.substring(before.length);
      tempNum = (new Array(after.length - tempNum.length + 1)).join('0') + tempNum;
      after = (tempNum.substring(0, tempNum.length - 1)).replace(/0*$/, '');

      num = (before || '0') + (after ? ('.' + after) : '');
    }
  }
  return num;
}
digitRound(1.255, 2)
>>> "1.26"

もっとスマートな方法がありそうな気がしてなりません。


修正@2007/05/20
0.xxとした際にうまく表示されなかったので修正しました。