>  기사  >  백엔드 개발  >  동일한 기본 배열을 공유할 때 Go 슬라이스에 추가하면 원본 슬라이스에 영향을 주지 않는 이유는 무엇입니까?

동일한 기본 배열을 공유할 때 Go 슬라이스에 추가하면 원본 슬라이스에 영향을 주지 않는 이유는 무엇입니까?

Barbara Streisand
Barbara Streisand원래의
2024-11-15 06:07:02209검색

Why doesn't appending to a Go slice affect the original slice when they share the same underlying array?

슬라이스의 추가 동작 이해

Go에서 슬라이스는 데이터 컬렉션을 관리하는 편리한 방법입니다. 그러나 특히 요소 추가와 같은 작업을 수행할 때 동작이 혼란스러울 수 있습니다.

다음 코드 조각을 고려하세요.

func main() {
    slice := make([]int, 10, 10)
    slice[0] = 0
    slice[1] = 1

    slice1 := slice
    slice1[0] = 10000
    fmt.Println(slice)

    slice1 = append(slice1, 100)
    slice1[0] = 20000

    fmt.Println(slice)
}

예상되는 출력은 첫 번째 슬라이스는 첫 번째 추가 후에 10000으로 변경되었고, 두 번째 추가 후에는 20000으로 변경되었습니다. 또한, 슬라이스와 슬라이스1 모두 동일한 기본 배열을 가리키기 때문에 슬라이스의 항목도 이러한 변경 사항을 반영할 것으로 예상됩니다.

그러나 실제 출력은 놀랍습니다.

[10000 1 0 0 0 0 0 0 0 0]
[10000 1 0 0 0 0 0 0 0 0]

예상한 대로 첫 번째 출력에서는 Slice1이 첫 번째 요소의 값을 10000으로 성공적으로 변경했음을 보여줍니다. 그러나 두 번째 출력에서는 후속 추가 작업과 Slice1에 대한 변경 사항이 Slice에 영향을 미치지 않았음을 보여줍니다. 왜 그럴까요?

Go의 가치 의미 이해

이 동작을 이해하는 열쇠는 Go의 가치 의미에 있습니다. Go에서는 변수가 값으로 전달됩니다. 즉, 변수를 다른 변수에 할당하면 값의 복사본이 만들어집니다. 이는 슬라이스에도 적용됩니다.

slice1 := 슬라이스를 수행하면 슬라이스 헤더의 복사본이 생성됩니다. 슬라이스 헤더에는 길이, 용량 및 기본 배열에 대한 포인터에 대한 정보가 포함되어 있습니다. 그러나 기본 배열 자체는 복사되지 않습니다.

추가 동작

추가 작업을 수행하면 새 슬라이스 헤더가 생성되고 새 기본 배열이 할당됩니다. . 원본 슬라이스의 요소가 새 배열에 복사되고 새 슬라이스 헤더가 반환됩니다.

이 예에서는 Slice1 = 추가(slice1, 100)를 수행하면 새 슬라이스 헤더가 생성되고 새로운 배열에는 기존 요소와 추가할 추가 요소를 위한 공간이 할당됩니다. Slice1의 요소가 새 배열에 복사되고 새 슬라이스 헤더가 Slice1에 할당됩니다.

중요한 점은 슬라이스가 여전히 원래 기본 배열을 가리키기 때문에 Slice1에 대한 변경 사항이 반영되지 않는다는 것입니다. Slice.

결론

슬라이스의 추가 동작을 이해하려면 슬라이스가 값으로 전달된다는 점을 기억하는 것이 중요합니다. 요소를 추가하면 새 슬라이스 헤더와 기본 배열이 생성되어 원래 슬라이스는 영향을 받지 않습니다.

위 내용은 동일한 기본 배열을 공유할 때 Go 슬라이스에 추가하면 원본 슬라이스에 영향을 주지 않는 이유는 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.