Programing

`copy ()`로 슬라이스를 복제 할 수없는 이유는 무엇입니까?

lottogame 2020. 8. 21. 08:28
반응형

`copy ()`로 슬라이스를 복제 할 수없는 이유는 무엇입니까?


Go에서 조각의 복사본을 만들고 문서를 읽어야하며 복사 기능이 있습니다.

내장 된 복사 함수는 소스 슬라이스의 요소를 대상 슬라이스로 복사합니다. (특별한 경우로 문자열의 바이트를 바이트 조각으로 복사합니다.) 소스와 대상이 겹칠 수 있습니다. Copy는 복사 된 요소의 수를 반환하며, 이는 len (src) 및 len (dst)의 최소값입니다.

하지만 내가 할 때 :

arr := []int{1, 2, 3}
tmp := []int{}
copy(tmp, arr)
fmt.Println(tmp)
fmt.Println(arr)

내는 tmp이전과 같이 비어 있습니다 (사용하려고 시도했습니다 arr, tmp).

[]
[1 2 3]

이동 놀이터 에서 확인할 수 있습니다 . 그렇다면 슬라이스를 복사 할 수없는 이유는 무엇입니까?


내장 copy(dst, src)min(len(dst), len(src))요소를 복사 합니다.

따라서 dst비어 있으면 ( len(dst) == 0) 아무것도 복사되지 않습니다.

tmp := make([]int, len(arr))( Go Playground ) 시도 :

arr := []int{1, 2, 3}
tmp := make([]int, len(arr))
copy(tmp, arr)
fmt.Println(tmp)
fmt.Println(arr)

출력 (예상대로) :

[1 2 3]
[1 2 3]

불행히도 이것은 builtin패키지에 문서화되어 있지 않지만 Go Language Specification : Appending to and copying slices에 문서화되어 있습니다 .

복사 된 요소의 수는 len(src)의 최소값입니다 len(dst).

편집하다:

마지막으로의 문서 copy()가 업데이트되었으며 이제 소스 및 대상의 최소 길이가 복사된다는 사실이 포함됩니다.

Copy는 복사 된 요소의 수를 반환하며, 이는 len (src) 및 len (dst) 최소값 입니다.


이를 수행하는 또 다른 간단한 방법 append은 프로세스에서 슬라이스를 할당하는 방법을 사용 하는 것입니다.

arr := []int{1, 2, 3}
tmp := append([]int(nil), arr...)  // Notice the ... splat
fmt.Println(tmp)
fmt.Println(arr)

출력 (예상대로) :

[1 2 3]
[1 2 3]

따라서 배열 복사의 약칭 arr은 다음과 같습니다.append([]int(nil), arr...)

https://play.golang.org/p/sr_4ofs5GW


조각의 크기 가 같으면 작동합니다 .

arr := []int{1, 2, 3}
tmp := []int{0, 0, 0}
i := copy(tmp, arr)
fmt.Println(i)
fmt.Println(tmp)
fmt.Println(arr)

줄 것 :

3
[1 2 3]
[1 2 3]

" Go Slices : 사용법 및 내부 "에서 :

복사 기능은 길이가 다른 슬라이스 간 복사를 지원합니다 ( 소수 요소까지만 복사합니다 ).

일반적인 예는 다음과 같습니다.

t := make([]byte, len(s), (cap(s)+1)*2)
copy(t, s)
s = t

copy ()는 dst와 src의 최소 길이로 실행되므로 dst를 원하는 길이로 초기화해야합니다.

A := []int{1, 2, 3}
B := make([]int, 3)
copy(B, A)
C := make([]int, 2)
copy(C, A)
fmt.Println(A, B, C)

산출:

[1 2 3] [1 2 3] [1 2]

append ()를 사용하여 nil 슬라이스에 모든 요소를 ​​한 줄에 초기화하고 복사 할 수 있습니다.

x := append([]T{}, []...)

예:

A := []int{1, 2, 3}
B := append([]int{}, A...)
C := append([]int{}, A[:2]...)
fmt.Println(A, B, C)    

산출:

[1 2 3] [1 2 3] [1 2]

할당 + 복사 ()와 비교하여 1,000 개 이상의 요소에 대해서는 append를 사용하십시오. 실제로 1,000 개 미만의 차이는 무시할 수 있습니다. 슬라이스가 많지 않은 경우 경험적으로 확인하세요.

BenchmarkCopy1-4                50000000            27.0 ns/op
BenchmarkCopy10-4               30000000            53.3 ns/op
BenchmarkCopy100-4              10000000           229 ns/op
BenchmarkCopy1000-4              1000000          1942 ns/op
BenchmarkCopy10000-4              100000         18009 ns/op
BenchmarkCopy100000-4              10000        220113 ns/op
BenchmarkCopy1000000-4              1000       2028157 ns/op
BenchmarkCopy10000000-4              100      15323924 ns/op
BenchmarkCopy100000000-4               1    1200488116 ns/op
BenchmarkAppend1-4              50000000            34.2 ns/op
BenchmarkAppend10-4             20000000            60.0 ns/op
BenchmarkAppend100-4             5000000           240 ns/op
BenchmarkAppend1000-4            1000000          1832 ns/op
BenchmarkAppend10000-4            100000         13378 ns/op
BenchmarkAppend100000-4            10000        142397 ns/op
BenchmarkAppend1000000-4            2000       1053891 ns/op
BenchmarkAppend10000000-4            200       9500541 ns/op
BenchmarkAppend100000000-4            20     176361861 ns/op

Go 프로그래밍 언어 사양

Appending to and copying slices

The function copy copies slice elements from a source src to a destination dst and returns the number of elements copied. Both arguments must have identical element type T and must be assignable to a slice of type []T. The number of elements copied is the minimum of len(src) and len(dst). As a special case, copy also accepts a destination argument assignable to type []byte with a source argument of a string type. This form copies the bytes from the string into the byte slice.

copy(dst, src []T) int
copy(dst []byte, src string) int

tmp needs enough room for arr. For example,

package main

import "fmt"

func main() {
    arr := []int{1, 2, 3}
    tmp := make([]int, len(arr))
    copy(tmp, arr)
    fmt.Println(tmp)
    fmt.Println(arr)
}

Output:

[1 2 3]
[1 2 3]

참고URL : https://stackoverflow.com/questions/30182538/why-cant-i-duplicate-a-slice-with-copy

반응형