boost:: IO service как гарантировать последовательность выполнения обработчика
У меня есть пул потоков с boost::io_service сверху. Я использую его для различных задач, связанных с процессором в целом приложении. Для некоторых задач я должен гарантировать, что задачи будут выполняться в указанном порядке (декодирование видеопотока). Использование io_service::strand гарантирует, что задачи не будут выполняться в данный момент, но у него нет никаких гарантий относительно порядка выполнения. Другими словами, задача №5 может быть выполнена до выполнения задачи №4. Существует ли какой-либо метод для решения этой проблемы, кроме планирования следующей задачи после выполнения текущей.
1 ответ:
strandобеспечивает гарантию того, что обработчики завершения не будут выполняться одновременно, и определяет порядок вызова обработчика. Короче говоря, обработчики завершения, разнесенные вstrand, выполняются в том же порядке, в котором они разнесены.Следовательно:
strand_.post(&task1); strand_.post(&task2); strand_.post(&task3);Гарантирует, что порядок вызова обработчика равен
task1->task2->task3. Однако обернутые обработчики завершения для асинхронных операций не гарантированы, так как порядок, в котором выполняются асинхронные операции исполняется неопределенно. Например, следующее не дает такой же гарантии:async_read(socket1, ..., strand_.wrap(&task1)); async_read(socket2, ..., strand_.wrap(&task2)); async_read(socket3, ..., strand_.wrap(&task3));Если обработчики завершения должны вызываться в указанном порядке для асинхронных операций, то либо:
- обработчики завершения очереди и управление заказом вручную.
- Сериализуйте все асинхронные операции. Например, обработчик завершения
async_op_1task1инициируетasync_op_2с обработчиком завершенияtask2.
Вот соответствующий отрывок: из
io_service::strand' s порядок вызова обработчика документация:Дано:
- прядильный объект
s- объект
a, удовлетворяющий требованиям обработчика завершения- объект
a1, являющийся произвольной копией объекта, созданного реализацией- объект
b, удовлетворяющий требованиям обработчика завершения- объект
b1, который является произвольной копией b, созданной реализациейЕсли какой-либо из справедливы следующие условия:
s.post(a)бывает-раньшеs.post(b)- ...
Затем
asio_handler_invoke(a1, &a1)случается-раньшеasio_handler_invoke(b1, &b1).
Comments