deepcopy.CopyEx
主要用于两个类型间的深度拷贝[从零实现]-这是新文档
本文是新文档,旧接口文档保持兼容性
- 支持异构结构体拷贝, dst和src可以是不同的类型,会拷贝dst和src交集的部分
- 多类型支持struct/map/slice/array/int...int64/uint...uint64/ 等等
- 性能相比json序列化和反序列化的做法,拥有更快的执行速度
- 可以控制拷贝结构体层次
- 可以通过tag控制感兴趣的字段
go get github.com/antlabs/deepcopy
package main
import (
"fmt"
"github.com/antlabs/deepcopy"
)
type dst struct {
ID int
Result string
}
type src struct{
ID int
Text string
}
func main() {
d, s := dst{}, src{ID:3}
deepcopy.CopyEx(&d, &s)
fmt.Printf("%#v\n", d)
}
如果src的结构体嵌套了两套,MaxDepth可以控制只拷贝一层
deepcopy.CopyEx(&dst{}, &src{}, deepcopy.WithMaxDepth(1))
只拷贝结构体里面有copy tag的字段,比如下面只会拷贝ID成员
package main
import (
"fmt"
"github.com/antlabs/deepcopy"
)
type dst struct {
ID int `copy:"ID"`
Result string
}
type src struct {
ID int `copy:"ID"`
Result string
}
func main() {
d := dst{}
s := src{ID: 3, Result: "use tag"}
deepcopy.CopyEx(&d, &s, deepcopy.WithTagName("copy"))
fmt.Printf("%#v\n", d)
}
package main
import (
"fmt"
"github.com/antlabs/deepcopy"
)
func main() {
i := []int{1, 2, 3, 4, 5, 6}
var o []int
deepcopy.CopyEx(&o, &i)
fmt.Printf("%#v\n", o)
}
package main
import (
"fmt"
"github.com/antlabs/deepcopy"
)
func main() {
i := map[string]int{
"cat": 100,
"head": 10,
"tr": 3,
"tail": 44,
}
var o map[string]int
deepcopy.CopyEx(&o, &i)
fmt.Printf("%#v\n", o)
}
经常看到,对同一个结构体的,有值更新操作,都是一堆手工if 然后赋值的代码。不仅容易出错,还累。快使用deepcopy解放双手。
type option struct {
Int int
Float64 float64
S string
}
func main() {
var a, b option
if b.Int != 0 {
a.Int = b.Int
}
if b.Float64 != 0.0 {
a.Float64 = b.Float64
}
if b.S != "" {
a.S = b.S
}
//可以约化成
deepcopy.CopyEx(&a, &b)
}
适合的场景是,比如把src里面的uid字段,拷贝到dst里面的uidString字段
var src = testSrcModifyMap{
I: 2,
}
var need = testDstModifyMap{
I8: 3,
}
var dst testDstModifyMap
err := CopyEx(&dst, &src, WithModifySrcField(map[string]ModifySrcValue{
"I": {
DstFieldName: "I8", SrcFieldName: "I", Callback: func(v interface{}) interface{} {
return int8(v.(int) + 1)
},
},
}))
if err != nil {
t.Errorf("test faild, err:%v", err)
}
if !reflect.DeepEqual(dst, need) {
t.Errorf("test faild, got:%v", dst)
}
从零实现的deepcopy相比json序列化与反序列化方式拥有更好的性能
goos: linux
goarch: amd64
pkg: github.com/antlabs/deepcopy
Benchmark_MiniCopy-16 159084 6737 ns/op
Benchmark_DeepCopy-16 374920 2895 ns/op
PASS
ok github.com/antlabs/deepcopy 2.275s