2016-08-21 24 views
0

我想分配值在init func中初始化的映射。分配到無地圖條目

但是出現恐慌: 分配進入未繳地圖

package main 

type Object interface { 
} 

type ObjectImpl struct { 
} 

type Test struct{ 
    collection map[uint64] Object 
} 

func (test Test) init(){ 
    test.collection = make(map[uint64] Object) 
} 

func main() { 
    test := &Test{} 
    test.init() 
    test.collection[1]=&ObjectImpl{} 
} 

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

回答

2

該函數Test的價值,所以它得到的它自己的副本。當函數返回時,對test Test的所有更改都將消失。通過指針以Test代替:

func (test *Test) init(){ 
    test.collection = make(map[uint64] Object) 
} 

不過要注意,該結構Test出口,該方法init不大,因此庫的用戶可能會創建一個Test但不正確初始化它。這似乎是圍棋界已建立了獨立NewType方法的約定:

type test struct{ 
    collection map[uint64] Object 
} 

function NewTest() *test { 
    return &test{ 
     collection: make(map[uint64] Object), 
    } 
} 

這確保了用戶只能通過調用NewTest獲得test和預期將被初始化。

+0

非常有意義,我不能相信我沒有意識到這一點我自己。謝謝你的答案和額外的一雙眼睛。 – Aidamina

1

你應該使用指針接收器的init方法:

func (test *Test) init() { // use a pointer to test 
    test.collection = make(map[uint64] Object) 
} 

沒有指針,要初始化地圖爲test對象的副本。實際的test對象永遠不會獲得初始化的映射。

Working Code