Использование cout в нескольких потоках может привести к чередующемуся выводу.
Поэтому я попытался защитить cout с помощью мьютекса.
Следующий код запускает 10 фоновых потоков с помощью std :: async.Когда поток запускается, он печатает "Запущенная тема ...".Основной поток перебирает фьючерсы фоновых потоков в том порядке, в котором они были созданы, и выводит «Done thread ...» после завершения соответствующего потока.
Вывод синхронизируется правильно, но через некоторое времяпотоки начались, а некоторые закончили (см. вывод ниже), возникает тупик.Все оставшиеся фоновые потоки и основной поток ожидают мьютекс.
В чем причина тупика?
Когда функция печати завершена или одна итерация цикла for завершается,lock_guard должен разблокировать мьютекс, чтобы один из ожидающих потоков мог продолжить работу.
Почему все темы остались голодными?
Код
#include <future>
#include <iostream>
#include <vector>
using namespace std;
std::mutex mtx; // mutex for critical section
int print_start(int i) {
lock_guard<mutex> g(mtx);
cout << "Started thread" << i << "(" << this_thread::get_id() << ") " << endl;
return i;
}
int main() {
vector<future<int>> futures;
for (int i = 0; i < 10; ++i) {
futures.push_back(async(print_start, i));
}
//retrieve and print the value stored in the future
for (auto &f : futures) {
lock_guard<mutex> g(mtx);
cout << "Done thread" << f.get() << "(" << this_thread::get_id() << ")" << endl;
}
cin.get();
return 0;
}
Выход
Started thread0(352)
Started thread1(14944)
Started thread2(6404)
Started thread3(16884)
Done thread0(16024)
Done thread1(16024)
Done thread2(16024)
Done thread3(16024)