>백엔드 개발 >Golang >범위 루프에서 포인터를 추가할 때 Go의 `append` 함수가 예상치 못한 결과를 생성하는 이유는 무엇입니까?

범위 루프에서 포인터를 추가할 때 Go의 `append` 함수가 예상치 못한 결과를 생성하는 이유는 무엇입니까?

Linda Hamilton
Linda Hamilton원래의
2024-12-22 22:35:15762검색

Why does Go's `append` function produce unexpected results when appending pointers from a for-range loop?

Go 슬라이스의 예기치 않은 추가 동작: 설명

Go에서 포인터 슬라이스에 추가할 때 추가 기능이 흥미롭게 작동합니다. 이를 설명하기 위해 다음 코드를 고려하십시오.

코드가 {0} {1} {2} {3}를 인쇄할 것이라는 기대와는 달리 대신 {0} {3} { 3} {3}. 이러한 불일치의 원인은 for 루프의 범위 변수의 특성에 있습니다.

범위 변수 이해

Go의 for-range 루프는 복사본을 생성하여 작동합니다. 반복되는 배열 또는 슬라이스의 각 요소. 이 경우 e는 배열 b에 있는 요소의 복사본입니다. 따라서 e 자체는 b의 요소가 아닙니다. 오히려 요소의 값을 보유하는 임시 변수입니다.

슬라이스 a에 추가할 때 코드는 b의 실제 요소 주소가 아닌 e의 주소를 추가합니다. e는 모든 반복에 대해 동일한 복사본이므로 동일한 포인터가 a에 세 번 추가됩니다. 따라서 e(Foo{3})에 할당된 마지막 값은 반복적으로 인쇄되는 값입니다.

동작 수정

이 동작을 수정하려면 코드 e의 주소가 아닌 b의 실제 요소 주소를 추가해야 합니다. 수정된 루프는 다음과 같습니다.

&e 대신 &b[i]를 추가하면 코드는 b의 각 요소가 a에 추가되도록 합니다. 결과적으로 올바른 출력 {0} {1} {2} {3}이 인쇄됩니다.

초기 동작 이유

이 예상치 못한 동작은 Go의 실제 참고 자료입니다. Go에는 포인터 유형과 포인터가 아닌 유형이 있지만 참조는 없습니다. 범위 변수는 포인터이거나 포인터가 아닌 값을 보유하는 단순한 지역 변수입니다. 참조를 보유할 수 없습니다.

따라서 범위 변수에 대해 작업을 수행할 때 요소 자체가 아닌 값만 조작하게 됩니다. 실제 요소를 수정하려면 값을 범위 변수에 할당하여 값을 효과적으로 복사해야 합니다. 그러면 이 값은 다음 반복에서 덮어쓰여집니다.

위 내용은 범위 루프에서 포인터를 추가할 때 Go의 `append` 함수가 예상치 못한 결과를 생성하는 이유는 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

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