В каком контейнере STL есть потокобезопасный процесс вставки? - PullRequest
5 голосов
/ 29 октября 2011

В каком контейнере STL есть процесс безопасной вставки потока? Я хочу, чтобы несколько потоков одновременно вставлялись в один контейнер. Любая реализация, кроме STL (т.е. Boost), приветствуется!

Ответы [ 6 ]

6 голосов
/ 29 октября 2011

Я пытаюсь избежать критической области в многопоточности, потому что это ухудшает производительность!

Наоборот, улучшает производительность. Поскольку блокировка контейнерного класса может быть только очень мелкозернистой, необходимо получить блокировку для каждой простой операции. Это дорого. Когда вы заботитесь о блокировке, у вас есть возможность приобрести замок и выполнить много операций. Это не улучшает шансы на параллелизм, но значительно снижает накладные расходы блокировки. Вы можете выбрать наиболее подходящую для вашего приложения стратегию, которая не навязывается вам.

Добавьте к этому, что практически невозможно написать поточно-ориентированную реализацию контейнера, которая не является ни склонной к тупику, ни очень дорогой. Итераторы являются проблемой. Автор библиотеки должен выбирать между принятием блокировки на время жизни итератора (рискуя зайти в тупик) или обновлять все действующие итераторы, когда другой поток изменяет коллекцию (дорого). Только дорогой выбор безопасен. Опять же, вы выбираете наиболее разумную стратегию, дорогой выбор не навязывается вам.

6 голосов
/ 29 октября 2011

Контейнеры STL не являются поточно-ориентированными.Вы должны навязать это сами, если пожелаете, с помощью собственной синхронизации.

3 голосов
/ 29 октября 2011

Стандарт не требует, чтобы контейнеры STL были поточно-ориентированными. Реализация может быть поточно-ориентированной, хотя я не уверен, как они справятся с текущим API; и изменение API сделает их более не совместимыми со стандартом.

Если LGPL является приемлемым, Intel TBB имеет поточно-ориентированные контейнеры (эти контейнеры используют внутренние блокировки, что влияет на их производительность).

2 голосов
/ 08 марта 2013

Взгляните на Boost.Lockfree (http://www.boost.org/doc/libs/1_53_0/doc/html/lockfree.html).. Предоставляет поточно-ориентированные реализации:

boost::lockfree::queue
  a lock-free multi-produced/multi-consumer queue
boost::lockfree::stack
  a lock-free multi-produced/multi-consumer stack
boost::lockfree::spsc_queue
  a wait-free single-producer/single-consumer queue (commonly known as ringbuffer)
1 голос
/ 29 октября 2011

Поскольку вы сказали, что любая другая (не STL) реализация приветствуется, я предлагаю Intel Thread Building Blocks. У них есть потокобезопасные параллельные контейнеры, которые имеют действительно хорошие рабочие характеристики.

1 голос
/ 29 октября 2011

Контейнеры следуют принципу KISS (Keep It Simple) и поэтому не имеют функций синхронизации.В большинстве случаев этой гипотетической встроенной синхронизации недостаточно, поскольку большую часть времени доступ к некоторым другим объектам должен быть синхронизирован с доступом к контейнеру.Комбинируйте свой контейнер с одним замком, и на этом все.

...