Home >Backend Development >Golang >Why Does Copying a Go Slice Not Create a Deep Copy, and How Can I Avoid Unintended Mutations?
Understanding Slice Mutability in Go
In Go, a slice is a dynamically sized variable that stores a contiguous sequence of elements. It is implemented using a header structure that stores the length and a pointer to the underlying array containing the elements.
Consider the following code snippet:
func someFunc(A []int) int { ... tempA := A // copy the slice by value ... newArr = remove(tempA, i) ... } func remove(slice []int, s int) []int { return append(slice[:s], slice[s+1:]...) }
In this code, the append function is used to modify the tempA slice. However, when the someFunc function returns, the original A slice is also modified, despite the fact that tempA was created as a copy of A.
Why does this happen?
A slice header is a separate data structure from the underlying array. When a slice is copied, only the header is copied, not the underlying array. This means that the original A slice and the newly created tempA slice both point to the same underlying array.
When the append function is called, a new slice is created and the elements of the tempA slice are copied into the new slice. However, the A slice still points to the same underlying array, which now contains the modified elements.
Recommendation
To avoid unintended mutations of the original slice when modifying a copy, you should use the copy function to create a deep copy of the slice. The copy function creates a new underlying array and copies the elements into it.
Here is an example of how to use the copy function:
tempA := make([]int, len(A)) copy(tempA, A)
This will create a new underlying array for tempA and copy the elements from A into it. Any modifications made to tempA will not affect the original A slice.
The above is the detailed content of Why Does Copying a Go Slice Not Create a Deep Copy, and How Can I Avoid Unintended Mutations?. For more information, please follow other related articles on the PHP Chinese website!