LLLit: Изучение и практика программирования

Имеет ли смысл производитель/потребитель boost::strand?

В этой записи блога (2010 г.) кто-то пытается решить Проблема производителя/потребителя с использованием средства Boost::strand. У меня такое ощущение, что он упустил суть и что его программа никогда не запускает одновременно какого-то производителя и какого-то потребителя, но я не настолько эксперт по библиотеке повышения, чтобы быть уверенным в этом.

  • У него есть только одна ветвь, по которой вызовы producer() и consumer() отправляются некоторыми таймерами;
  • У него два потока, оба вызывают io_service::run()

Тем не менее, только одна цепочка с гарантией того, что «ни один из этих обработчиков не будет выполняться одновременно», также означает, что мы будем либо создавать или одновременно, в то время как я бы скажем, ничто не должно мешать производителю производить единицу U+t, пока потребитель использует единицу U, верно?

   void producer_consumer::producer() {
     if ( count_ < num)   {
       ++count_;
       intvec_.push_back(count_);
       std::cout << count_ < " pushed back into integer vector." << std::endl;
       timer1_.async_wait(strand_.wrap(
           boost::bind(&producer_consumer::producer, this))); // loops back
       timer2_.async_wait(strand_.wrap(
           boost::bind(&producer_consumer::consumer, this))); // start consumer
     }
   }

Или я упускаю из виду тот факт, что какой-то File::async_read() будет принимать функцию "производства" с обертыванием цепочек в качестве обратного вызова завершения и аналогичный Socket::ready-to-write-again, который объясняет, что его предложение имеет смысл, пока " производитель ()» и «потребитель ()» на самом деле являются частями, защищенными монитором, которые взаимодействуют с общим буфером?


  • Из блога у меня сложилось впечатление, что автор предлагает использовать strand Boost.Asio для синхронизации, а не другие конструкции синхронизации, когда это возможно, и предоставил упрощенный пример для демонстрации использования strand. Лично я не согласен с этим тезисом, так как предпочитаю использовать strand когда это имеет смысл, а не когда это возможно, и обнаружил отсутствие подтверждающих доказательств, поскольку последствия являются результатом многопоточность, а не механизм синхронизации. 30.09.2013

Ответы:


1

Пример кода больше ориентирован на демонстрацию strand как механизма синхронизации, чем на решение проблема производителя и потребителя.

В качестве мотивационного случая использования strand для решения проблемы производитель-потребитель рассмотрим клиент чата на основе графического интерфейса, использующий TCP. Графический интерфейс пользователя может создавать несколько сообщений, пытаясь отправить сообщение до того, как предыдущее сообщение будет записано в соединение. Между тем, приложение должно потреблять и записывать каждое сообщение в соединение TCP, сохраняя при этом сообщения, что приводит к отсутствию чередования данных. Составные операции, такие как async_write требует, чтобы поток не выполнял никаких других операций записи, пока не завершится составная операция. Для учета такого поведения:

  • Очередь может буферизовать сообщения чата.
  • The GUI can post an operation into strand that will:
    • Add the chat message to the queue.
    • Условно запустите потребитель.
  • Потребитель — это асинхронная цепочка вызовов, которая читает из очереди и записывает в сокет в пределах strand.

См. этот ответ для реализации.

30.09.2013
  • Условно запуская потребителя, я полагаю, вы подразумеваете существование некоторого вызова wake_thread_now(), который не помешает потоку перейти в спящий режим позже, если он проснется прямо сейчас. 02.10.2013
  • Между тем, мне кажется, что если у нас есть очередь, она решает проблему prod/cons, которую вы представили своим простым присутствием (если только нажатие в очередь не может заблокировать поток графического интерфейса). 02.10.2013
  • @sylvainulg: Условное начало намеренно расплывчато. Это может быть какой-то wake_thread_now(), но он также может запускать асинхронную цепочку, как показано в связанном ответе (цепочка write() -> writeHandler()). С тем, как работает strand, более вероятно, что графический интерфейс создаст операцию для помещения в очередь и немедленного возврата, а не напрямую поместит в очередь, где она может заблокироваться. 02.10.2013
  • Новые материалы

    CS373 Summer 2018: Миранда Фуленчек
    CS373 Summer 2018: Миранда Фуленчек Неделя 1: 4 июня — 10 июня Что вы делали на прошлой неделе? Занятия начались на этой неделе, поэтому большую часть времени я потратил на..

    Как развивается смешанно-целочисленное программирование, часть 7
    Унифицированная техника раннего завершения для первично-двойственных алгоритмов в смешанно-целочисленном коническом программировании (arXiv) Автор : Ювэнь Чэнь , Кэтрин Нин , Поль Гулар..

    Как научить модель Keras распознавать текст переменной длины
    Я некоторое время играл с официальным примером Keras image_ocr.py и хочу поделиться своими выводами в этом посте. В официальном примере выполняется только обучение модели, но отсутствует..

    Практическая пакетная нормализация
    История начинается после использования инициализации He вместе с ELU (или любым вариантом ReLU) может значительно снизить опасность проблем с исчезающими/взрывающимися градиентами в начале..

    Поэзия онлайн-кодирования: путешествие пикселей и страсти
    В мире, наполненном инновациями, онлайн-обучение программированию становится холстом, на котором обретает форму полотно вашей мечты. Это больше, чем просто создание строк кода; это сродни..

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

    Ограничение скорости в .NET Core 7 Web API
    Что такое ограничение скорости? Ограничение скорости — это процесс, используемый для ограничения количества запросов, разрешенных для определенного ресурса в указанном временном окне. .NET..