Best way in Java to convert a double (representing a price) to a long with a price scale of 8

huangapple go评论73阅读模式
英文:

Best way in Java to convert a double (representing a price) to a long with a price scale of 8

问题

在使用Java代码表示价格的情况下,将double转换为具有8位价格精度的long的最佳方法是什么?例如,{Double} 17.99 应该转换为 {Long} 1799000000。这个double可能包含2到4位小数。

以下简单的代码有时可以正确工作:

Double dprice = 17.99;
Long lprice = (long) (dprice * 100000000);

然而,出于已知的原因(参考浮点数指南),它可能会产生意外的结果。例如,在一个测试中,{Double} 17.99 转换为 {Long} 1798999999。

在Java中,有哪些最佳选项可以安全地进行这种转换?在这种情况下,是否需要使用BigDecimal?

英文:

In Java code where a double is used to represent a price, what is the best way to convert the double to a long with a price scale of 8? For example, {Double} 17.99 would convert to {Long} 1799000000. The double may contain 2 to 4 decimal places.

Simple code such as the following sometimes works correctly:

 Double dprice = 17.99;
 Long lprice = (long) (dprice * 100000000);

However, for known reasons (floating point guide), it may create an unexpected result. For example, in one test {Double} 17.99 converts to {Long} 1798999999.

What are the best options in Java to safely do this conversion? Is BigDecimal necessary in this case?

答案1

得分: 1

为了保持精度,正如Andy Turner在评论中指出的,您必须在进行乘法等操作时使用BigDecimal,直到最后。以下代码应该可以工作:

import java.math.BigDecimal;
import java.math.RoundingMode;

class Main {
  public static void main(String[] args) {
    BigDecimal dprice = BigDecimal.valueOf(17.99).setScale(2, RoundingMode.HALF_UP);
    Long lprice = dprice.multiply(BigDecimal.valueOf(100000000)).longValue();
    System.out.println(lprice);
  }
}

setScale 调用可以用来设置您希望保留的小数位数的精确值。

英文:

In order to keep the precision, as Andy Turner pointed out in the comments, you have to use BigDecimals when doing the multiplications, etc, until the very end. The following should work:

import java.math.BigDecimal;
import java.math.RoundingMode;

class Main {
  public static void main(String[] args) {
    BigDecimal dprice = BigDecimal.valueOf(17.99).setScale(2, RoundingMode.HALF_UP);
    Long lprice = dprice.multiply(BigDecimal.valueOf(100000000)).longValue();
    System.out.println(lprice);
  }
}

The setScale call can be used to set the exact amount of decimal digits you would like to keep.

huangapple
  • 本文由 发表于 2020年4月6日 05:28:29
  • 转载请务必保留本文链接:https://go.coder-hub.com/61049751.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定