四捨五入について
んー、これバカっぽぃネタですけども。
ちょっとカスタムでサブルーチンを定義するのもなんかこそばゆい。
従って後者の場合。
Math::Round::nearestを使う場合
小数点第2位を四捨五入して小数点第1位まで丸めたい場合、Math::Roundを使うと、
$ perl -MMath::Round -e 'for (my $i = 0.01; $i <= 0.1; $i += 0.01) { my $j = 1.0 + $i; printf("%.2f -> %.2f\n", $j, Math::Round::nearest(.1, $j)) }'
1.01 -> 1.00
1.02 -> 1.00
1.03 -> 1.00
1.04 -> 1.00
1.05 -> 1.10
1.06 -> 1.10
1.07 -> 1.10
1.08 -> 1.10
1.09 -> 1.10
1.10 -> 1.10うん、きちんと四捨五入されてますね。
printfのみ
ちなみにsprintf("%.1f", 1.05)でも似たようなroundが出来ます。
$ perl -e 'for (my $i = 0.01; $i <= 0.1; $i += 0.01) { my $j = 1.0 + $i; printf("%.2f -> %.2f\n", $j, sprintf("%.1f", $j)); }';
1.01 -> 1.00
1.02 -> 1.00
1.03 -> 1.00
1.04 -> 1.00
1.05 -> 1.10
1.06 -> 1.10
1.07 -> 1.10
1.08 -> 1.10
1.09 -> 1.10
1.10 -> 1.10有効なソースは見つからないんだけど、隣のだにたん*1の環境では四捨五入にはならなかった。
もうちょっと詳しく(追記)
どうも演算の仕方によっては誤った結果が返ってくる場合があるみたいです。
上のforループでの演算と直接例えば1.14, 1.15とかを一個ずつprintfでroundすると、
$ perl -e 'my $n = 1.14; printf("%.1f\n", $n);' 1.1
$ perl -e 'my $n = 1.15; printf("%.1f\n", $n);' 1.1ってなります。
これは次のような比較をすると分かるかな。
$ perl -e 'printf("%.20f, %.20f\n", 1.15, 1.10 + 0.05);'
1.14999999999999991118, 1.15000000000000013323