go json反系列化精度丢失问题

场景说明:
在go语言开发当中,作为中间转发业务 , 往往会在json反系列过程中使用interface来接受任意类型的值,来实现对数据的透明化 ,以便提高业务拓展性,但这情况在反系列化中可能会遇到精度丢失问题,主要表现为uint64、int64类型json反系列化成interface类类型后精度丢失问题。
比如一个精度丢失的例子:

package main
import (
	"encoding/json"
	"log"
)
type Info struct {
	Mode int
	Stu student
}
type student struct {
	ID uint64 `json:"id"`
	Age int `json:"age"`
	Name string `json:"name"`
}
type InfoType struct {
	Mode int
	Stu interface{}
}
func main(){
	//源头json数据
	InfoData := Info{
		Mode: 1,
		Stu: student{
			ID:   9223372036854775807,
			Age:  21,
			Name: "xiaoming",
		},
	}
	data , _ := json.Marshal(InfoData)
	//中间转发业务 使用interface 来表示student info
	var Info InfoType
	json.Unmarshal(data , &Info)
	jsonData , _ := json.Marshal(Info.Stu)
	//处理中间转发业务发来的Stu信息
	var stuInfo student
	json.Unmarshal(jsonData , &stuInfo)
	log.Printf("stuInfo:%+v" , stuInfo)
}

结果为:

stuInfo:{ID:9223372036854776000 Age:21 Name:xiaoming}

由9223372036854775807转变为了9223372036854776000,但如果值不大时,就不会出现精度问题
解决方式:
1、使用json的useNumber属性

//中间转发业务 使用interface 来表示student info
	var Info InfoType
	d := json.NewDecoder(bytes.NewReader(data))
	d.UseNumber()
	_ = d.Decode(&Info)

精度丢失的原因分析:默认情况 ,数值类型(int、int64…)json 反系列化成interface类型时,会转为float64类型。即inut64或者uint64转为float64会存在精度丢失的问题。
在这里插入图片描述
解决方案分析:json 反系列过程有一个变量useNumber控制数字类型反系列为interface的类型只要有两种,一个是float64,一个是Number(本质就是string类型—type Number string),使用Number类型,相当于数字型 转为string,就会避免精度丢失问题。
2、使用string表示遇到uint64、int64类型的
**注意:**int64或者uint64并非任何值转float64都是精度丢失,只有超过一定的范围值时,才会出现精度丢失问题

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值