빈 슬라이스를 초기화하는 올바른 방법


227

크기가 고정되지 않은 빈 슬라이스를 선언하는 것이 좋습니다.

mySlice1 := make([]int, 0)

또는:

mySlice2 := []int{}

어느 것이 올바른 방법인지 궁금합니다.


2
"고정되지 않은 크기"라고 말하지만 슬라이스의 크기는 고정되어 있지 않습니다 . 용량이 0을 의미하지 않는 한. 필요한 용량에 대한 아이디어 / 추측 / 힌트가 있다면 세 가지 인수 버전을 사용하는 것이 좋습니다. 예 : 맵 키 조각을 만들려면 :keys := make([]int, 0, len(m)); for k, v := range m { keys := append(keys,k) }
Dave C

답변:


272

두 가지 대안은 의미 상 동일하지만 사용 make([]int, 0)하면 runtime.makeslice (Go 1.14) 에 대한 내부 호출이 발생 합니다.

nil값 을 그대로 두는 옵션도 있습니다 .

var myslice []int

에 기록 된대로 Golang.org 블로그 :

nil 슬라이스는 아무것도 가리지 않더라도 기능적으로 길이가 0 인 슬라이스와 같습니다. 길이가 0이며 할당과 함께 추가 할 수 있습니다.

nil슬라이스 그러나됩니다 json.Marshal()"null"빈 슬라이스로 마샬링하는 반면 "[]"@farwayer에 의해 지적 아웃으로.

@ArmanOrdookhani가 지적한 것처럼 위의 옵션 중 어느 것도 할당을 유발하지 않습니다.



106
수주의 : json.Marshal()반환 null을 위해 var myslice []int[]초기화 슬라이스myslice := []int{}
farwayer

10
또한주의 : reflect.DeepEqual전무 조각 및 비 무기 호 조각 사이의 구분한다 : a := []int{}, var b []int,reflect.DeepEqual(a, b) // returns false
asgaines

1
왜 할당을 할 것이라고 생각합니까? 캡이 0이므로 할당 된 것이 없습니다. 길이가 0 인 항목에 대한 모든 포인터는 메모리에서 동일한 위치를 가리 킵니다. play.golang.org/p/MPOKKl_sYvw
Arman Ordookhani

1
@ArmanOrdookhani 맞습니다. 나는 그것을 시험해 보았고 동일한 조립 지침에 대한 가정에 틀렸다는 것을 알았습니다. 결정된!
ANisus

65

그것들은 동등합니다. 이 코드를 참조하십시오 :

mySlice1 := make([]int, 0)
mySlice2 := []int{}
fmt.Println("mySlice1", cap(mySlice1))
fmt.Println("mySlice2", cap(mySlice2))

산출:

mySlice1 0
mySlice2 0

두 슬라이스 모두 0용량이있어 두 슬라이스 모두0 길이를 수 있습니다 (용량보다 클 수 없음). 두 슬라이스 모두 요소가 없음을 의미합니다. 이것은 2 개의 슬라이스가 모든 측면에서 동일하다는 것을 의미합니다.

비슷한 질문을보십시오 :

골랑에 닐 슬라이스와 빈 슬라이스가있는 점은 무엇입니까?

Go 언어의 nil 조각과 non-nil 조각과 빈 조각


46

@ ANisus의 답변 외에도 ...

아래는 "실제로 이동" 책 의 일부 정보입니다 .

nil& empty조각의 차이점

다음과 같이 슬라이스를 생각하면 :

[pointer] [length] [capacity]

그때:

nil slice:   [nil][0][0]
empty slice: [addr][0][0] // points to an address

무 슬라이스

슬라이스를 반환하는 함수에서 예외가 발생하는 경우와 같이 존재하지 않는 슬라이스를 나타내려는 경우에 유용합니다.

// Create a nil slice of integers.
var slice []int

빈 조각

빈 조각은 데이터베이스 쿼리가 결과를 0으로 반환하는 경우와 같이 빈 컬렉션을 나타내려는 경우에 유용합니다.

// Use make to create an empty slice of integers.
slice := make([]int, 0)

// Use a slice literal to create an empty slice of integers.
slice := []int{}

에 관계없이 당신이 전무 슬라이스 또는 빈 슬라이스, 내장 기능을 사용하고 있는지 여부 append, len그리고 cap같은 일을.


운동장 예 :

package main

import (
    "fmt"
)

func main() {

    var nil_slice []int
    var empty_slice = []int{}

    fmt.Println(nil_slice == nil, len(nil_slice), cap(nil_slice))
    fmt.Println(empty_slice == nil, len(empty_slice), cap(empty_slice))

}

인쇄물:

true 0 0
false 0 0

make?를 사용하여 빈 슬라이스의 주소를 한 단계로 얻을 수 있습니까 ?
Simin Jie

우리는 기능을 살펴 가지고가는 경우에 서명 , make주소를 반환하지 않는 것 같습니다. 한 번에 할 수 없다고 생각합니다.
tgogos

13

빈 슬라이스와 nil 슬라이스는 Go에서 다르게 초기화됩니다.

var nilSlice []int 
emptySlice1 := make([]int, 0)
emptySlice2 := []int{}

fmt.Println(nilSlice == nil)    // true
fmt.Println(emptySlice1 == nil) // false
fmt.Println(emptySlice2 == nil) // false

세 조각 모두 len과 cap은 0입니다.


make([]int, 0)Jetbrains GoLand는 "불필요하다"고 불평하지 않기 때문에 최고입니다 []int{}. 이것은 단위 테스트를 작성하는 데 유용합니다.
Andrzej Rehmann
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.