java struts2 奇怪的序列化行为(自行舍入大数字)

Posted

技术标签:

【中文标题】java struts2 奇怪的序列化行为(自行舍入大数字)【英文标题】:java struts2 weird serialization behavior (rounds big numbers by its self) 【发布时间】:2013-05-31 20:46:08 【问题描述】:

我有下一个孤立的测试用例场景

@SMDMethod
public BigInteger getSomeReallyBigInteger() 
    return new BigInteger("154456875042019001");

这是 struts.xml 中的操作

    <action name="DataSourceRpc" class="isoblock.struts2.action.DataSourceAction" method="smd">
        <interceptor-ref name="json">
            <param name="enableSMD">true</param> 
        </interceptor-ref>
        <result type="json">
            <param name="enableSMD">true</param>
        </result>
    </action>

我使用 JSON-RPC 实现(使用 dojo-rpc)调用 SMD 函数,这是失败,

当我调用最后一个函数时,结果回调它:

154456875042019000

而不是

154456875042019001

这种情况只发生在大数字(全部有 17 个或更多 dijit),我使用 struts2-json-plugin-2.3.8.jar(最新)

所以,这是一个 struts2 错误吗??

你好,

【问题讨论】:

【参考方案1】:

问题是javascript中的数字是双精度浮点数,不能准确表示154456875042019001。双精度浮点数的精度为 15-17 位,而您有 18 位。当转换为浮点数并再次返回时,会丢失一些精度。

例如,在 Perl 中:

$a=154456875042019001.0;
printf "%20d",$a;

输出

154456875042019008

更多细节:

15445687504201900110 的十六进制表示形式是 0x0224bdb5a1ff16b9,它包含 58 个有效位(在二进制中它以 0000 0010 0010 0100 ... 开头,因此 64 减去 6 个前导零位)。双精度浮点数的精度为 52 位,因此在将 64 位 long 转换为 double 时会丢失一些位。

【讨论】:

hm,所以这意味着我必须返回一个字符串而不是一个数字??谢谢:) 这是一种方法,而且可能是最好的方法。

以上是关于java struts2 奇怪的序列化行为(自行舍入大数字)的主要内容,如果未能解决你的问题,请参考以下文章

PostgreSQL JDBC 驱动程序舍入双倍值

天蓝色专用 sql 池 (sqldw) 可序列化表提示语句奇怪的行为

WCF 奇怪的行为

Quarkus 和 Jackson 奇怪的龙目岛行为

Gson toJson(),奇怪的行为(产生空的 json)

时间序列中 pandas .agg 的奇怪行为