SoFunction
Updated on 2025-03-05

Detailed explanation of Golang's medium and deep copy and shallow copy

What is a deep copy?

Deep Copy means that the original object and the copied new object are independent of each other, and changes to any of the objects will not affect the other object. The data of value types is a deep copy by default, such as array, int, string, struct, float, and bool types.

What is a shallow copy?

Shallow Copy refers to copying part of one object into another object, using a pointer to reference the original object, thereby realizing partial copying of the original object. At this time, the memory address pointed to by the new object and the old object is the same. After modifying the new object value, the old object value will also change. Data of reference types are shallow copies by default, such as slice and map.

Sample code

For reference type objects, using equal sign assignment is a shallow copy, see the following code snippet:

package main

import (
	"fmt"
	"reflect"
	"unsafe"
)

func main() {
	slice1 := []int{1, 2, 3, 4, 5, 6}

	//slice2 is a shallow copy of slice1	slice2 := slice1
	(slice1)
	(slice2)

	//Modify the value of slice1, the value of slice2 will also change	slice1[1] = 100
	(slice1)
	(slice2)

	//The addresses of slice1 and slice2 are the same	("slice1 address:", (*)((&slice1)))
	("slice2 address:", (*)((&slice2)))
}

After running, the output is as follows:

[1 2 3 4 5 6]
[1 2 3 4 5 6]
[1 100 3 4 5 6]
[1 100 3 4 5 6]
slice1 address: &{824633811232 6 6}
slice2 address: &{824633811232 6 6}

It can be seen that the addresses of the two objects are the same.

To implement deep copy of slice, you need to use the copy method. The copy method returns the result as an int value, indicating the length of the copy from the original slice to the destination slice. When using the copy method, you need to initialize the length of the target slice first:

  • If the length of dst is less than the length of src, copy some of the contents in src;
  • If it is greater than, all copies will be copied and the remaining space will fill the default value of the type;
  • If it is equal, it happens to be no more or less copy, so dst usually specifies its length as src when initialized.

Examples are as follows:

package main

import (
	"fmt"
	"reflect"
	"unsafe"
)

func main() {
	src := []int{1, 2, 3, 4, 5, 6}

	//Output the initial and value of src	("src length:", len(src), "src:", src)
	//Output the src address	("src address:", (*)((&src)))

	dst1 := make([]int, 2)
	copy(dst1, src)
	("dst1 length:", len(dst1), "dst1:", dst1)
	("dst1 address:", (*)((&dst1)))

	dst2 := make([]int, len(src))
	copy(dst2, src)
	("dst2 length:", len(dst2), "dst2:", dst2)
	("dst2 address:", (*)((&dst2)))

	dst3 := make([]int, len(src)+2)
	copy(dst3, src)
	("dst3 length:", len(dst3), "dst3:", dst3)
	("dst3 address:", (*)((&dst3)))
}

The output is as follows:

src length: 6 src: [1 2 3 4 5 6]
src address: &{824633811232 6 6}
dst1 length: 2 dst1: [1 2]
dst1 address: &{824633819808 2 2}
dst2 length: 6 dst2: [1 2 3 4 5 6]
dst2 address: &{824633811280 6 6}
dst3 length: 8 dst3: [1 2 3 4 5 6 0 0]
dst3 address: &{824633843904 8 8}

It can be seen that the addresses of the new object and the original object are different.

summary

A deep copy is to create a new object that completely copies the original object and all its nested objects, so the new object is a separate copy of the original object, and subsequent modifications will not affect the original object. The shallow copy only copies the address reference of the data structure of the original object. Therefore, the references of the new object and the original object point to the same underlying data structure, and modifications to the new object will also affect the original object.

This is the end of this article about the detailed explanation of Golang's deep copy and shallow copy. For more related Golang's deep copy and shallow copy content, please search for my previous articles or continue browsing the related articles below. I hope everyone will support me in the future!