web日常开发中,往往需要转换数据对象,比如DTO转Entity、Entity转DTO。为了高性能,我们有必要了解一下那种方式效率更高,消耗更低。下面进行基准测试。
环境准备
go.14
goland
三种方式
- 属性直接赋值。
- 标准库的encoding/json。
- 号称宇宙最快的json-iterator。
简单的测试代码
package mainimport("encoding/json""github.com/json-iterator/go")type Entity struct {id stringname stringkey stringaddr string}type DTO struct {id stringname stringkey stringaddr string}func main() {}func conver() {entity := Entity{id: "11111",name: "11111",key: "11111",addr: "11111",}_ = DTO{id: entity.id,name: entity.name,key: entity.key,addr: entity.addr,}}func converJson() {entity := Entity{id: "11111",name: "11111",key: "11111",addr: "11111",}j,_:=json.Marshal(entity)_ = json.Unmarshal(j,&DTO{})}func converJson2() {var json =jsoniter.ConfigCompatibleWithStandardLibraryentity := Entity{id: "11111",name: "11111",key: "11111",addr: "11111",}j,_:=json.Marshal(entity)_ = json.Unmarshal(j,&DTO{})}
基准测试代码
package mainimport ("testing")func BenchmarkConver(b *testing.B) {b.SetParallelism(1)b.ReportAllocs()b.RunParallel(func(pb *testing.PB) {for pb.Next(){conver()}})}func BenchmarkConverJson(b *testing.B) {b.SetParallelism(1)b.ReportAllocs()b.RunParallel(func(pb *testing.PB) {for pb.Next(){converJson()}})}func BenchmarkConverJson2(b *testing.B) {b.SetParallelism(1)b.ReportAllocs()b.RunParallel(func(pb *testing.PB) {for pb.Next(){converJson2()}})}
测试结果
执行命令
$ go test ./... -bench="."
BenchmarkConver-8 1000000000 0.162 ns/op 0 B/op 0 allocs/opBenchmarkConverJson-8 16866072 72.1 ns/op 320 B/op 5 allocs/opBenchmarkConverJson2-8 24555042 49.4 ns/op 130 B/op 3 allocs/op
可以看出最快最省的是直接赋值。是最快的json转换304倍,是标准库的445倍。不过如果一定需要使用json转换的建议使用github.com/json-iterator/go这个库,从测试结果来看,比标准库少了2次内存分配,执行耗时只有标准库的68%,内存占用只有标准库的40%。