Example situation:
There's a global struct holding a slice of structs.
type stctUser struct {
user string
privilege int
created time.Time
}
type stctAllUsers struct {
sync.RWMutex
slcUsers []stctUser
}
var strctAllUsers stctAllUsers
There's a function that wants to operate on the users, and to reduce the time it's locking that global struct, I want to grab a user and release the lock
var strctUserTemp stctUser
strctAllUsers.RLock
for a := range strctAllUsers.slcUsers {
if tmpName == strctAllUsers.slcUsers[a].user {
strctUserTemp = strctAllUsers.slcUsers[a]
break
}
}
strctAllUsers.RUnlock
Is strctUserTemp working with a separate copy of slcUsers[a], or is it a pointer to that element of the slice? For example, strctAllUsers.slcUsers[a] is "Tom" and changing strctUserTemp.user = "Bob", would strctAllUsers.slcUsers[a] still be Tom?
(Before, it seems that making a copy of a slice to a new variable would mean changes to that new variable slice could change the original...so it assigned a pointer instead of creating a copy. Or am I misremembering?)
Update: Seeing as I was too stupid to take five minutes to test this out...here's a link to the behavior that had me questioning this in the first place, and I wanted to clarify the implementation before assuming I understood what was happening and creating a bug in the actual stuff I was working on. https://play.golang.org/p/ndmJ0h1z-sT
Most importantly: assignment always copies. However, it could be a copy of a pointer.
There are three basic scenarios:
myVar := &mySlice[0]
). The local variable contains a copy of the reference created by the addressing expression. Changes to the local variable's value are reflected by any other use of the slice element, because the local pointer points directly to the memory where that slice element is held.Note that the last option means you'll have a fragile pointer - if you append to the slice and the underlying array moves around in memory you'll get some confusing behavior.