这是我的示例:
class MyController {
def index() {
JSONObject json = request.JSON
log.info('{}', json)
respond json
}
}
如何处理json中的BigInteger?像这样:
curl -H 'content-type: application/json' -d '{"largeNum": 99999999999999999999999}' http://localhost:8080/
JSONObject会将这个
largeNum
转换为Double
,如下所示:{"largeNum":9.999999999999999E22}
但是我想获得一个BigInteger,怎么办?
最佳答案
问题出在Grails JSON实现中。request.JSON
调用grails.converters.JSON
,后者再使用org.grails.web.json.JSONTokener
类来解析输入。
重要的代码形式org.grails.web.json.JSONTokener#nextValue
是:
try {
return Integer.valueOf(s);
} catch (Exception e) {
try {
return Long.valueOf(s);
} catch (Exception f) {
try {
return Double.valueOf(s);
} catch (Exception g) {
return s;
}
}
}
这将导致精度损失,并且无法更改行为,
因为此标记生成器是在自定义编码器起作用之前使用的。
我想到的唯一解决方案是使用GSON或Jackson。
该代码取自
grails 3.3.0
。我不知道那是从那以后。关于JSON数字:
如果没有具体的格式,Java中的大多数json解析器会将json编号视为
BigDecimal
,因为json编号没有限制,并且BigDecimal
是唯一可以正确表示的Java类型-请参见JSON Spec这似乎很尴尬,因为JSON代表Java脚本对象表示法,而Javascript无法处理这些数字。