Store based on previous value
german94 opened this issue · comments
Germán commented
Hello,
First of all thanks for this package, I really like it and I'm using it in a few of my side projects.
I just wanted to ask something regarding the MapOf
type. Is there a way to store for a key, based on the previous value, atomically?
For example, I'm doing this:
var new []string
old, ok := ms.data.Load(id)
if ok {
new = old
}
new = append(new, values...)
ms.data.Store(id, new)
however I'd like to do it in an atomic way, everything in a function.
Thanks.
Andrei Pechkurov commented
Thanks for the feedback!
As for updating a value atomically, that's simple. You just need to use Compute
method:
func main() {
ms := xsync.NewMapOf[int, []string]()
id := 42
values := make([]string, 3)
// Update the value atomically.
v, ok := ms.Compute(id, func(oldValue []string, loaded bool) (newValue []string, delete bool) {
if loaded { // Existing key case
// It's important to allocate a new slice each time we mutate a value.
// That's to avoid races with concurrent readers.
newValue = append(make([]string, 0, len(oldValue)+len(values)), oldValue...)
newValue = append(newValue, values...)
} else { // New key case
newValue = values
}
delete = false
return
})
fmt.Printf("v: %v, ok: %v\n", v, ok)
}