C#で端数の切り上げってどうやるの?
切り下げ(捨て)、四捨五入についても知りたい
丸める桁を指定できないかな……
小数点以下の切り上げなどの処理を行いたいことって、結構ありますよね。
そんなとき、どのメソッドを使えば良いか、それぞれどう違うかって悩んでしまいますよね。
こんにちは、エンジニアでC#ライターの遠藤です!
今回の記事では、数値の切り上げ、切り下げ、四捨五入処理のメソッドの紹介・比較をします。
この記事では以下のような方に向けて書きました。
- C#で小数点以下の切り上げがしたい方
- 切り下げ(捨て)、四捨五入についても知りたい方
- 丸める桁数を指定できるか知りたい方
前提知識: 使用するメソッドと桁の処理について
今回の記事では、細かい解説を後にして先に使うメソッド等の知識をまとめます。
まず、今回使うメソッドは以下の通りです。
- 切り上げ: Math.Ceiling()
- 切り下げ(捨て): Math.Floor(), Math.Truncate()
- 四捨五入: Math.Round()
また、結論として切り上げ、切り捨てのメソッドでは丸める桁の指定はできません。もし特定の桁を丸めたい場合は、元の数の桁をシフトして上記のメソッドで処理する必要があります。
四捨五入を行うMath.Round()では桁の指定ができます。
以降の章では、それぞれの具体的な使い方と違いについて紹介します。
切り上げの方法
まずは切り上げの方法について解説します。
切り上げでは、Math.Ceiling()を使って実装します。
using System;
class Program
{
public static void Main()
{
double val = 1.2345;
Console.WriteLine(Math.Ceiling(val));
Console.WriteLine(Math.Ceiling(-val));
}
}
実行結果:
2 -1
特に変哲のない切り上げですが、負の値の場合は正の方向へ切り上げになるので注意してください。
切り下げの方法
今度は切り下げです。切り下げでは、Math.Floor()とMath.Truncate()の2種類があります。
using System;
class Program
{
public static void Main()
{
double val = 1.25;
Console.WriteLine("+Floor: " + Math.Floor(val));
Console.WriteLine("+Truncate: " + Math.Truncate(val));
Console.WriteLine("-Floor: " + Math.Floor(-val));
Console.WriteLine("-Truncate: " + Math.Truncate(-val));
}
}
実行結果:
+Floor: 1 +Truncate: 1 -Floor: -2 -Truncate: -1
上記のようにFloor()とTruncate()では、正の値では同じ結果ですが負の値では違う結果となります。
この違いは、切り下げと切り捨ての違いとして出ています。その違いとしては切り下げが負の方向へ値を丸めるのに対し、切り捨ては0に向けて値を丸めます。
C#ではFloorは切り下げ、Truncateが切り捨てですね。この違いがあることを知らないと、累積すると大きな差になってしまうので注意が必要です。
四捨五入する方法
最後に四捨五入です。こちらはMath.Round()を使います。
using System;
class Program
{
public static void Main()
{
Console.WriteLine(Math.Round(1.5));
Console.WriteLine(Math.Round(2.5));
Console.WriteLine(Math.Round(-1.5));
Console.WriteLine(Math.Round(-2.5));
}
}
実行結果:
2 2 -2 -2
「え、おかしくない!?」と思いますよね。Roundは引数を指定しない場合、最も近い偶数に向けて四捨五入します。
蛇足にはなりますが、これは銀行家が使っていたことから「銀行丸め」と言います。この計算方法の方が累積したときに実際の値と近くなりやすいそうです。
話は戻りまして、通常の四捨五入を行いたい場合はRoundに”MidpointRounding.AwayFromZero”を引数に入れる必要があります。
using System;
class Program
{
public static void Main()
{
Console.WriteLine(Math.Round(1.5, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(2.5, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(-1.5, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(-2.5, MidpointRounding.AwayFromZero));
}
}
実行結果:
2 3 -2 -3
これで最も近い整数に四捨五入されました。
特定の桁を丸めたい時は
特定の桁を丸めたいとき、まずRound()で四捨五入する場合は、引数を追加するだけで指定できます。
using System;
class Program
{
public static void Main()
{
Console.WriteLine(Math.Round(1.15, 1, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(1.25, 1, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(-1.15, 1, MidpointRounding.AwayFromZero));
Console.WriteLine(Math.Round(-1.25, 1, MidpointRounding.AwayFromZero));
}
}
実行結果:
1.2 1.3 -1.2 -1.3
意味としては、第2引数に小数第何位まで表示したいかを記載する形となります。今回は”1″を入れたので、小数第2位で四捨五入が行われ、小数第1位までが表示されています。
またこの場合も”AwayFromZero“が無いと銀行丸めになるので要注意です。
つづいて切り上げ・切り下げ(捨て)の場合ですが、こちらは冒頭でも説明した通り桁数の指定ができません。そのため、丸めが行われる桁に合わせて元の値をシフトする必要があります。
using System;
class Program
{
public static void Main()
{
double val = 1.2345; //小数第1位まで表示させたい
val = val * 10;
Console.WriteLine("+Floor: " + (Math.Floor(val) / 10));
Console.WriteLine("+Truncate: " + (Math.Truncate(val) / 10));
Console.WriteLine("-Floor: " + (Math.Floor(-val) / 10));
Console.WriteLine("-Truncate: " + (Math.Truncate(-val) / 10));
}
}
実行結果:
+Floor: 1.2 +Truncate: 1.2 -Floor: -1.3 -Truncate: -1.2
まとめ
今回の記事では、以下の点について解説致しました。
- C#の値の切り上げについて
- 切り下げ・切り捨てについて
- 四捨五入について
- 特定の桁を丸めたい時の実装方法について
数値処理を行う場合は、切り上げ等の処理を使うケースがしばしばあるかと思います。
ここで違いと使い方を覚えて、役立ててください!