How to initialize elements in a Go structure

I'm new to Golang, so highlighting in it makes me insane:

import "sync" type SyncMap struct { lock *sync.RWMutex hm map[string]string } func (m *SyncMap) Put (k, v string) { m.lock.Lock() defer m.lock.Unlock() m.hm[k] = v, true } 

and then I just call:

 sm := new(SyncMap) sm.Put("Test, "Test") 

At this moment, I get a panic with a null pointer.

I worked on it using another function and call it right after new() :

 func (m *SyncMap) Init() { m.hm = make(map[string]string) m.lock = new(sync.RWMutex) } 

But I wonder if it is possible to get rid of this template initialization?

+49
new-operator go
Dec 21 '10 at 11:58
source share
3 answers

You just need a constructor. The common pattern used is

 func NewSyncMap() *SyncMap { return &SyncMap{hm: make(map[string]string)} } 

If your structure has more fields, starting with goroutine as a backend or registering a finalizer, all this can be done in this constructor.

 func NewSyncMap() *SyncMap { sm := SyncMap{ hm: make(map[string]string), foo: "Bar", } runtime.SetFinalizer(sm, (*SyncMap).stop) go sm.backend() return &sm } 
+62
Dec 21 '10 at 12:45
source share

The "Mue" solution does not work because the mutex is not initialized. The following modification works:

 package main import "sync" type SyncMap struct { lock *sync.RWMutex hm map[string]string } func NewSyncMap() *SyncMap { return &SyncMap{lock: new(sync.RWMutex), hm: make(map[string]string)} } func (m *SyncMap) Put (k, v string) { m.lock.Lock() defer m.lock.Unlock() m.hm[k] = v } func main() { sm := NewSyncMap() sm.Put("Test", "Test") } 

http://play.golang.org/p/n-jQKWtEy5

+9
Nov 10
source share

Good catch from deamon. Mew may have thought of a more common scheme for including locking as a value rather than a pointer. Since a null Mutex value is ready-to-use unlocked Mutex, it does not require initialization and includes one value that is shared. As a further simplification, you can insert it by omitting the field name. Then your structure gets a set of Mutex methods. See This Working Example, http://play.golang.org/p/faO9six-Qx . I also took the use of deferment. To some extent, this is a matter of preference and coding style, but since it has a small overhead, I try not to use it in small functions, especially if there is no conditional code.

+5
Nov 10 '12 at 20:57
source share



All Articles