Приведённый код уже защищает map с помощью одного RWMutex. При доступе только через эти функции ошибки concurrent map read and map write быть не должно.
Синхронный доступ к общей map в Go
Приведённый код уже защищает map с помощью одного RWMutex. При доступе только через эти функции ошибки concurrent map read and map write быть не должно.
Короткий ответ
Что ответить на собеседовании
Подробный разбор
Ответ с пояснениями
Условие
В программе объявлена глобальная карта map[string]int, к которой из разных горутин одновременно выполняются операции чтения и записи. При этом приложение падает с ошибкой fatal error: concurrent map read and map write. Необходимо подобрать подходящий механизм синхронизации, который устранит эту проблему.
package main
import (
"fmt"
"sync"
"time"
)
var (
mu sync.RWMutex
m = map[string]int{"a": 1}
)
func main() {
go read()
time.Sleep(1 * time.Second)
go write()
time.Sleep(1 * time.Second)
}
func read() {
for {
mu.RLock()
fmt.Println(m["a"])
mu.RUnlock()
}
}
func write() {
for {
mu.Lock()
m["a"] = 2
mu.Unlock()
}
}
Ответ
Приведённый код уже защищает map с помощью одного RWMutex. При доступе только через эти функции ошибки concurrent map read and map write быть не должно.
Чтение выполняется между RLock/RUnlock, запись — между Lock/Unlock. Если авария остаётся, ищите другие обращения к m без того же mutex или копирование объекта синхронизации.
Улучшите read: скопируйте значение под read-lock, снимите его и только затем вызывайте Println, чтобы медленный вывод не удерживал блокировку. Бесконечные циклы создают нагрузку; добавьте управляемое завершение через context и ожидание работников вместо Sleep в main. Порядок конкретных значений 1 и 2 не следует использовать как синхронизацию.