round/floor/ceilと丸めモードの使い分け

round/floor/ceilは数値を丸める関数で、それぞれ四捨五入・切り捨て・切り上げを行います。roundは桁数や丸めモードも指定でき、用途で使い分ける書き方です。

三つの丸めの基本

数値の丸めは round()(四捨五入)、floor()(切り捨て=負の無限大方向)、ceil()(切り上げ=正の無限大方向)が基本です。名前は知っていても、負の数での挙動を取り違えることがあるので、そこは一度確認しておくと安心ですね。

echo round(2.5);  // 3
echo floor(2.9);  // 2
echo ceil(2.1);   // 3

// 負の数での方向に注意
echo floor(-2.1); // -3 (小さいほうへ)
echo ceil(-2.9);  // -2 (大きいほうへ)

floor() / ceil() は float を返すので、整数として使いたいなら (int) でキャストするか、intdiv などを検討することになると思います。

精度指定で小数桁を丸める

round() は第2引数で小数点以下の桁数を指定できます。金額表示で2桁にそろえたり、逆に負の桁を指定して10や100の位で丸めたりもできます。ここは floor() / ceil() には無い機能なので、桁指定の丸めが必要なら round が候補になりますね。

echo round(3.14159, 2); // 3.14
echo round(2.675, 2);   // 2.68 (ただし float 誤差に注意)

// 負の精度で上の桁を丸める
echo round(12345, -2);  // 12300
echo round(12345, -3);  // 12000

ちなみに round(2.675, 2) が期待どおりにならない場合があるのは、2.675 が float で正確に表せないからです。厳密さが要るなら bcmath 側で処理するほうが確実だと思います。

PHP_ROUND_HALF_* で丸め方を選ぶ

ちょうど 0.5 のときどちらへ丸めるかは、第3引数のモードで制御できます。既定は PHP_ROUND_HALF_UP(0.5 は遠いほうへ=いわゆる四捨五入)ですが、銀行丸め(偶数丸め)にしたいときは PHP_ROUND_HALF_EVEN を使います。統計処理や会計で偏りを避けたいときに効きますね。

echo round(2.5, 0, PHP_ROUND_HALF_UP);   // 3
echo round(2.5, 0, PHP_ROUND_HALF_DOWN); // 2
echo round(2.5, 0, PHP_ROUND_HALF_EVEN); // 2 (偶数へ)
echo round(3.5, 0, PHP_ROUND_HALF_EVEN); // 4 (偶数へ)

まとめ

丸めは、方向が決まっているなら floor() / ceil()、桁数やモードを制御したいなら round()、と用途で選ぶのが素直です。負の数での方向と、0.5 の丸め方(HALF_UP か HALF_EVEN か)を意識しておくと事故が減ります。float 誤差が絡む厳密な金額計算では、round に頼りすぎず bcmath へ寄せるのが安全だと思います。

よくある質問

Q. floor/ceilの戻り値は整数ですか。
A. いいえ、floatを返します。整数として使いたいなら (int) でキャストしてください。

Q. 小数第2位で丸めたいときは。
A. round($v, 2) のように第2引数で桁数を指定します。負の桁を指定すれば10や100の位でも丸められます。

Q. 0.5の丸め方を変えたいときは。
A. 第3引数のモードで制御します。銀行丸め(偶数丸め)にしたいときは PHP_ROUND_HALF_EVEN を使います。

類似投稿

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です