Какие операции являются потокобезопасными на std:: map?
Супы, которые у меня есть:
stl::map<std::string, Foo> myMap;
является безопасным потоком данных?
myMap["xyz"] ?
т.е. Я хочу иметь эту гигантскую карту только для чтения, которая распределяется между многими потоками; но я не знаю, можно ли даже искать его в потоковом режиме.
Спасибо!
EDIT:
Все сначала написано.
Затем после этого из него читаются несколько потоков.
Я пытаюсь избежать блокировок, чтобы сделать это как можно скорее. (возможно, я знаю возможную преждевременную оптимизацию)
Ответы
Ответ 1
Теоретически, контейнеры STL не являются потокобезопасными. На практике чтение безопасно, если контейнер не изменяется одновременно. т.е. стандарт не содержит никаких спецификаций о потоках. Следующая версия стандарта будет и IIUC, после чего она будет гарантировать безопасное поведение в режиме readonly.
Если вы действительно обеспокоены, используйте отсортированный массив с бинарным поиском.
Ответ 2
С++ 11 требует, чтобы все функции-члены, объявленные как const
, были потокобезопасными для нескольких читателей.
Вызов myMap["xyz"]
не является потокобезопасным, поскольку std::map::operator[]
не объявляется как const
.
Вызов myMap.at("xyz")
является потокобезопасным, хотя, поскольку std::map::at
объявлен как const
.
Ответ 3
Как минимум в реализации Microsoft, чтение из контейнеров является потокобезопасным (ссылка).
Однако std::map::operator[]
может изменять данные и не объявляться const
. Вместо этого вы должны использовать std::map::find
, который const
, чтобы получить const_iterator
и разыскать его.
Ответ 4
Теоретически, структуры и функции только для чтения не требуют блокировок для обеспечения безопасности потоков. Он по своей сути является потокобезопасным. В параллельных чтениях памяти нет расы данных. Однако вы должны гарантировать безопасную инициализацию только одним потоком.
Как указал Макс С., в основном реализация чтения элемента на карте типа myMap["xyz"]
не имела бы операций записи. Если это так, то это безопасно. Но, опять же, вы должны гарантировать, что нет нити, которая изменяет структуру, кроме фазы инициализации.
Ответ 5
Коллекции STL не являются потокобезопасными, но довольно просто добавить безопасность потоков к одному.
Лучше всего создать оболочку потокобезопасности вокруг рассматриваемой коллекции.