In scenarios where multiple threads operate concurrently in Go, ensuring safe data access is crucial. This article explores a scenario where a main thread requires data collection from worker threads without compromising thread safety.
Scenario
The main thread creates multiple worker threads, each running in its own goroutine and incrementing an iteration count at regular intervals. Every 10 seconds, the main thread aims to collect iteration counts from workers and display consolidated statistics.
Question
Given that the main thread only reads while individual threads write, is it safe to directly access values? How can this be implemented effectively?
Answer
Directly reading values from different threads without synchronization is inherently unsafe in Go, as it may exhibit undefined behavior. To ensure data integrity, some form of synchronization is necessary.
Implementation Considerations
The suggested solution utilizes a sync.RWMutex to protect the shared data. When workers write to the iteration count, they acquire a write lock, and when the main thread reads, it acquires a read lock.
Example Code Using sync.RWMutex
type Worker struct { iterMu sync.RWMutex iter int } func (w *Worker) Iter() int { w.iterMu.RLock() defer w.iterMu.RUnlock() return w.iter } func (w *Worker) incIter() { w.iterMu.Lock() w.iter++ w.iterMu.Unlock() }
Alternatively, the sync/atomic package can be used to manage thread-safe data modifications, as demonstrated in the following code:
Example Code Using sync/atomic
type Worker struct { iter int64 } func (w *Worker) Iter() int64 { return atomic.LoadInt64(&w.iter) } func (w *Worker) incIter() { atomic.AddInt64(&w.iter, 1) }
The above is the detailed content of How to Safely Read Values from Multiple Goroutines in Go?. For more information, please follow other related articles on the PHP Chinese website!