1. 序章

ご存知のように、丸めを行うと、精度が犠牲になりますが、数値が短く単純になります。

このチュートリアルでは、Kotlinで数値を丸めることができるいくつかの方法を見ていきます。

2. BigDecimalによる丸め

BigDecimal クラスは、Double数値を簡単に丸める方法を提供します。

val rawPositive = 0.34444
val roundedUp = rawPositive.toBigDecimal().setScale(1, RoundingMode.UP).toDouble()
assertTrue(roundedUp == 0.4)

setScale()を使用して、Doubleを丸める必要のある小数点以下の桁数を指定します。 これを説明するために、スケールを2に設定しましょう。

val roundedUp = rawPositive.toBigDecimal().setScale(2, RoundingMode.UP).toDouble()
assertTrue(roundedUp == 0.35)

示されているように、スケールを2に設定すると、数値は小数点以下2桁に丸められます。

また、丸めモードを指定することもできます。 たとえば、 RoundingMode.UP を使用すると、ゼロから丸めることができます。

RoundingMode.HALF_UP は、丸めの一般的な方法です。 これは、学校で一般的に教えられている丸めモードでもあります。

同様に、 RoundingMode.DOWN を設定すると、数値をゼロに切り捨てることができます。

val rawPositive = 0.34444
val rawNegative = -0.3444

val roundedDown = rawPositive.toBigDecimal().setScale(1, RoundingMode.DOWN).toDouble()
assertTrue(roundedDown == 0.3)

val roundedDownNegative = rawNegative.toBigDecimal().setScale(1, RoundingMode.DOWN).toDouble()
assertTrue(roundedDownNegative == -0.3)

丸めモードをに設定します RoundingMode.DOWNまた、スケールを1に設定します 。 予想どおり、数値はゼロに向かって小数点以下1桁に切り捨てられます。

使用できる丸めモードは他にもたくさんあります。

たとえば、RoundingMode.CEILINGは正の無限大に丸められます。

val roundedCeiling = rawPositive.toBigDecimal().setScale(1, RoundingMode.CEILING).toDouble()
assertTrue(roundedCeiling == 0.4)

同様に、RoundingMode.FLOORは負の無限大に向かって丸めます。

val roundedFloor = rawPositive.toBigDecimal().setScale(1, RoundingMode.FLOOR).toDouble()
assertTrue(roundedFloor == 0.3)

さらにいくつかの丸めモードがあります。

val roundedHalfUp = 1.55.toBigDecimal().setScale(1, RoundingMode.HALF_UP).toDouble()
assertTrue(roundedHalfUp == 1.6)

val roundedHalfEven = 1.55.toBigDecimal().setScale(1, RoundingMode.HALF_EVEN).toDouble()
assertTrue(roundedHalfEven == 1.6)

val roundedHalfDown = 1.55.toBigDecimal().setScale(1, RoundingMode.HALF_DOWN).toDouble()
assertTrue(roundedHalfDown == 1.5)

これらのモードはすべて、最も近いネイバーに向かって丸められます。 ただし、隣人が同じように離れている場合は、動作が異なります

  • RoundingMode.HALF_UP切り上げ
  • RoundingMode.HALF_DOWN切り捨て
  • RoundingMode.HALF_EVEN最も近い偶数の隣人に向かって

3. String.format()を使用する

String.format()を使用して10進数を丸めることもできます。

val raw1 = 0.34
val raw2 = 0.35
val raw3 = 0.36

val rounded1: Double = String.format("%.1f", raw1).toDouble()
assertTrue(rounded1 == 0.3)

val rounded2: Double = String.format("%.1f", raw2).toDouble()
assertTrue(rounded2 == 0.4)

val rounded3: Double = String.format("%.1f", raw3).toDouble()
assertTrue(rounded3 == 0.4)

ここで、 String.format()はRoundingMode.HALF_UPのように動作します。 ただし、丸めモードを変更する方法はありません。

また、ロケールの指定を検討する必要があります。 そうすることで、英語以外のロケールでのエラーを回避します。 この例としては、フランス語またはスラブ語のロケールがあります。

val rounded: Double = String.format("%.1f", raw1).toDouble()

デフォルトのロケールがLocale.Frenchの場合に上記のコードを実行すると、 NumberFormatExceptionが発生します。これを処理するには、Localeを指定する必要があります。

val rounded: Double = String.format(Locale.ENGLISH, "%.1f", raw1).toDouble() 
assertTrue(rounded == 0.3)

4. DecimalFormatを使用する

String.format()と同様に、 DecimalFormatを使用して数値をフォーマットできます。

val df = DecimalFormat("#.#", DecimalFormatSymbols(Locale.ENGLISH))
val raw1 = 0.34.toBigDecimal()
val raw2 = 0.35.toBigDecimal()
val raw3 = 0.36.toBigDecimal()

val rounded = df.format(raw1).toDouble()
assertTrue(rounded == 0.3)

val rounded = df.format(raw2).toDouble()
assertTrue(rounded == 0.4)

val rounded = df.format(raw3).toDouble()
assertTrue(rounded == 0.4)

ここ、 RoundingMode.HALF_EVENがデフォルトで使用されます。 丸めモードを指定することもできます

val df = DecimalFormat("#.#", DecimalFormatSymbols(Locale.ENGLISH))
df.roundingMode = RoundingMode.FLOOR

val rounded3Floor = df.format(raw3).toDouble()
assertTrue(rounded3Floor == 0.3)

5. 結論

要約すると、Kotlinでさまざまな方法で丸めを実行できますが、選択する方法はユースケースによって異なります。

いつものように、コードサンプルはGitHubにあります。