首页   注册   登录
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX  ›  程序员

后台 long 类型在 js 中丢失精度的问题大家是怎么解决的?

  •  
  •   xiangyuecn · 41 天前 · 1436 次点击
    这是一个创建于 41 天前的主题,其中的信息可能已经有所发展或是发生改变。

    查了一下 JavaScript 能处理的最大整数为 Math.pow(2, 53) == 9007199254740992。9007199254740992+1 就开始不能正确表示了。

    后端数据中有些 long 类型的数据(比如 id 生成器生成的 long 类型 id ),如果直接发数字给前端,就会出问题。

    但一棍子打死全部 long 类型转成字符串好像也比较困难。想了一下,全转成字符串操作起来有点复杂,一不留神就会遗漏。而且因为 long 类型包含 int 类型范围,有可能因为测试值并未超过 js 的最大精度,漏转的地方会成为难以排查的隐藏 bug。

    v 友们遇到过这种问题吗,要怎样方便的解决?

    19 回复  |  直到 2019-01-12 03:56:49 +08:00
        1
    shapl   41 天前   ♥ 1
        2
    lzxz1234   41 天前
    一棍子打死全部 long 类型转成字符串好像也比较困难
    找对地方,一点也不困难
        3
    wenzhoou   41 天前 via Android
    个人认为既然是 ID,你又不拿它做数字运算。那就应该定义成字符串类型。岂不妙哉。
        4
    66beta   41 天前 via Android
    同楼上,你是 ID,又不做运算,字符串有什么还担心的
        5
    VDimos   41 天前 via Android
    用第三方库
        6
    supuwoerc   41 天前
    不做运算直接 String 岂不妙哉
        7
    xiangyuecn   41 天前
    @66beta @wenzhoou
    我也是这样想的,ID 这种处理起来比较简单。但 long 类型并不只是 id 会用到啊。可能某些计算结果也是 long 类型,如果忘记处理成 string,不就出乱子了么,而且忘记处理的有点难排查,因为测试时这个 long 值可能比较小,测试时不会出问题,就埋了个雷。

    @lzxz1234 #2 这个地方难找,昨晚想了一晚上 还失眠了
        8
    xiangyuecn   41 天前
    @shapl 厉害了这个 js 库,拿来用了
        9
    lzxz1234   41 天前   ♥ 1
    你要把数据返给前端,肯定有个地方进行序列化吧,可能是模板可能是 json,在这定制个规则加上引号就行了
        10
    wenzhoou   41 天前 via Android
    非 ID 的话。具体问题具体分析吧。

    a 系统和 b 系统的数值范围不一致,这很正常。前端到后台,后台到数据库和别的系统,数值不一致这种事情多了。

    你把前端的取值范围调大了。前端的数据往后台系统传的时候,也有可能越界啊。

    不过,你把后台系统的 long 型定为标准,原则上也是没有问题的。

    问题能解决就好。
        11
    lolizeppelin   41 天前   ♥ 1
    用 jsonlint 加 long.js 解决

    这样 json 解析的时候 超过长度的会返回的就是一个 Long 对象

    数字处理会方便点...
        12
    xiangyuecn   41 天前
    @lzxz1234 嗯,json 数据 我研究一下是后端处理简单还是前端处理简单
        13
    lolizeppelin   41 天前
    随便看了下 1 楼的库, 就代码行数上来看太简单了很有可能 json 解析并不靠谱

    应该不如 jsonlint

    虽然我都没认真读过里面代码, 但是 jsonlint 原理上屌不少 23333
        14
    brucewuio   40 天前
    分开咯 比如 2 个 int 自己写个能满需求的
        15
    zouqiang   40 天前
    json 序列化的时候转 string
        16
    DOLLOR   40 天前
    https://github.com/MikeMcl?tab=repositories
    这位仁兄写的几个 2K+Stars 工具都挺不错的,可以操作大数字,可以选一个试试。
        17
    vigossliao   40 天前
    这些工具库还是没有解决掉本质的问题

    而且忘记处理的有点难排查,因为测试时这个 long 值可能比较小,测试时不会出问题,就埋了个雷。


    某个字段可能出现 但是没有处理 或者 忘记处理了 或者 不知道那个字段会出现这个问题

    就算前端有各种工具库来处理都是无济于事
    除非前端在涉及到 number 的时候都用工具库来处理
        18
    LeoEatle   40 天前
    先考虑这个数据是用作什么的,id 的话完全可以转字符串
        19
    zzjas98   40 天前
    最近 Chrome 出了一个对 BigInt 的 type 的支持。是作为浏览器内的 primitive type 支持的,应该效果不错。但是跨浏览器原生支持好像还不是很全。

    > BigInts are a new numeric primitive in JavaScript that can represent integers with arbitrary precision.

    想了解的话可以看看这些链接
    Spec: https://tc39.github.io/proposal-bigint/
    Coverage: https://caniuse.com/#search=bigint
    Chrome Implementation: https://developers.google.com/web/updates/2018/05/bigint

    总而言之是个挺新的东西,不一定现在有用,但是楼主不妨了解一下没准过段时间就能广泛使用了。
    关于   ·   FAQ   ·   API   ·   我们的愿景   ·   广告投放   ·   感谢   ·   实用小工具   ·   3405 人在线   最高记录 4385   ·  
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.3 · 18ms · UTC 05:30 · PVG 13:30 · LAX 21:30 · JFK 00:30
    ♥ Do have faith in what you're doing.
    沪ICP备16043287号-1