先看几个完整的例子:

func DeepCopy(dst, src interface{}) error {
	var buf bytes.Buffer
	if err := gob.NewEncoder(&buf).Encode(src); err != nil {
		return err
	}
	return gob.NewDecoder(bytes.NewBuffer(buf.Bytes())).Decode(dst)
}

type User struct {
	Name  string
}

func main() {
	fmt.Println("引用类型,直接赋值浅拷贝:")
	user1 := &User{
		Name:  "why",
	}
	user2 := user1
	fmt.Println(*user1)
	fmt.Println(*user2)
	user1.Name = "jzm"
	fmt.Println(*user1)
	fmt.Println(*user2)
	fmt.Println("\n")



	fmt.Println("值类型,直接赋值深拷贝:")
	user3 := User{
		Name:  "why",
	}
	user4 := user3
	fmt.Println(user3)
	fmt.Println(user4)
	user4.Name = "jzm"
	fmt.Println(user3)
	fmt.Println(user4)
	fmt.Println("\n")


	fmt.Println("引用类型,DeepCopy深拷贝:")
	user5 := &User{
		Name:  "why",
	}
	user6 := new(User)
	fmt.Println(*user5)
	fmt.Println(*user6)
	DeepCopy(user6, user5)
	user6.Name = "jzm"
	fmt.Println(*user5)
	fmt.Println(*user6)
	fmt.Println("\n")


	fmt.Println("值类型,DeepCopy深拷贝:")
	user7 := User{
		Name:  "why",
	}
	user8 := new(User)
	fmt.Println(user7)
	fmt.Println(*user8)
	DeepCopy(user8, user7)
	user8.Name = "jzm"
	fmt.Println(user7)
	fmt.Println(*user8)
	fmt.Println("\n")
[why@whydeMacBook-Pro] ~/Desktop/go/test$go run main.go 
引用类型,直接赋值浅拷贝:
{why}
{why}
{jzm}
{jzm}


值类型,直接赋值深拷贝:
{why}
{why}
{why}
{jzm}


引用类型,DeepCopy深拷贝:
{why}
{}
{why}
{jzm}


值类型,DeepCopy深拷贝:
{why}
{}
{why}
{jzm}

结论:

  • 不带&实例化的结构体,是值类型,赋值是深拷贝。
  • & 和 new 实例化的结构体,都是引用类型,赋值都是浅拷贝。
  • 无论是引用类型还是值类型,通过序列化 - 反序列化的方式,都可以转为深拷贝。