【问题标题】:Hibernate is rounding my double?Hibernate 正在舍入我的两倍?
【发布时间】:2010-12-07 06:00:15
【问题描述】:

我有一个 double,我正试图将其保存到 postgres 数字列中。

我要保存的值是 151.33160591125488,我已经验证这实际上是 Hibernates 内部预插入接收到的参数。

但是数据库post insert中的值是151.331605911255,即四舍五入到12dp。

我知道我的列具有正确的比例,因为它是一个不受限制的数字列,并且以下...

update tbl set col=151.33160591125488

...达到预期效果。

所以罪魁祸首必须是 Hibernate 或 postgres-JDBC 驱动程序。

想法?

编辑:

org.hibernate.dialect.PostgreSQL方言:

registerColumnType( Types.DOUBLE, "float8" );

select cast (151.33160591125488 as float8);

=151.331605911255

因此 double 的默认行为是不正确的,因为它并不总是保存提供给它的 double。

有谁知道如何让休眠状态在 postgres 中使用“数字”列类型?

【问题讨论】:

  • 您在休眠方面没有提供足够的详细信息。映射可以指定精度和比例。例如:
  • 谢谢布赖恩,我会尝试这样做,但是这会降低我的应用程序的可扩展性,这一切都是因为休眠行为不端。 java double不限制,postgres不限制,为什么要休眠?
  • 我尝试了 precision="30" scale="20" 这应该已经足够了,同样的结果。这么糟糕的建议。
  • 仅供参考,“postgres”标签最近已替换为“postgresql”。请参阅meta.stackexchange.com/questions/25279/… 了解更多信息。我冒昧地重新标记了这个问题。
  • 仅供参考,precision="12" scale="2" 对插入/更新没有影响,只有当 hibernate 也创建数据库时才使用它,以便它知道如何创建列。

标签: java hibernate postgresql jdbc


【解决方案1】:

Java double 并不适合精确的数学运算。请改用 BigDecimal。 Hibernate 支持它作为basic types 之一:

<property name="amount" type="big_decimal" />

【讨论】:

  • 算术与否并不重要。您不能依赖double来获得任何种精度。此外,您还问过如何映射到“NUMERIC”类型 - 这就是“big_decimal”所映射的内容。
  • 给我看一个不执行算术的双重变化的例子。
【解决方案2】:

只要精度很重要,请使用java.math.BigDecimalanswer 对此进行了非常详细的讨论。

【讨论】:

  • 谢谢,我相信这会起作用(我会测试它),但是由于我不对这个数字执行任何算术运算,因此 IEEE 陷阱不适用。因此 double 非常适合我的需要。 hibernate 无意中更改我要求它保留的一条信息仍然没有意义。
  • 来自 JLS (java.sun.com/docs/books/jls/third_edition/html/typesValues.html) 浮点类型为 float,其值包括 32 位 IEEE 754 浮点数和 double,其值包括 64- bit IEEE 754 浮点数。 因此不管你有没有做过任何计算,你仍然有陷阱。
  • 怎么回事?我有一个确切的双。我需要它坚持下去。它没有改变。如果 hibernate 没有将它转换为 float8 ,它将被正确地持久化。根据我的经验,当您对这些数字进行算术运算时,您只会遇到 IEEE 754 的问题。证明我是错的。举个例子。
  • 使用 BigDecimal 进行测试 - 这是不可接受的。它返回一个无效的数字。例如: System.out.println(new BigDecimal(-33.62112355233672)); = -33.62112355233671934229278122074902057647705078125。我知道我可以设置精度/比例,但重点是我想要一个真正的浮点数。我不想要固定比例。所以要使用 bigdecimal,我必须先询问我的 double,弄清楚它如何使用 dp,然后将其设置在 BigDecimal 上?
  • 另外,-33.62112355233672 相当于 -33.62112355233672000000000000000000000000000000000 不是 -33.621123552336719342292581220749021
猜你喜欢
  • 1970-01-01
  • 2013-08-22
  • 1970-01-01
  • 2014-01-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-09-07
  • 2015-01-26
相关资源
最近更新 更多