fork(2) download
  1. #include <iostream>
  2. #include <stdexcept>
  3. #include <vector>
  4. #include <memory>
  5. #include <chrono>
  6. #include <thread>
  7. #include <mutex>
  8. #include <queue>
  9. #include <condition_variable>
  10. #include <atomic>
  11. #include <utility>
  12. #include <cassert>
  13. using namespace std;
  14. using namespace std::chrono;
  15.  
  16.  
  17. #define CONCURRENT
  18.  
  19. #define N_GRAPHICS (1 * 1000 * 1000)
  20. #define N_THREADS 8
  21.  
  22.  
  23.  
  24. struct Graphic;
  25.  
  26. static vector<size_t> indexes;
  27. static vector<unique_ptr<Graphic>> graphics;
  28.  
  29. static queue<pair<Graphic*, size_t>> q;
  30. static mutex m;
  31. static atomic<size_t> n_elements;
  32.  
  33.  
  34. struct Graphic
  35. {
  36. Graphic()
  37. : status(false)
  38. {
  39. }
  40.  
  41.  
  42. bool parse()
  43. {
  44. // waste time
  45. try
  46. {
  47. throw runtime_error("");
  48. }
  49. catch (runtime_error)
  50. {
  51. }
  52.  
  53. status = true;
  54. //return false;
  55. return true;
  56. }
  57.  
  58.  
  59. bool status;
  60. };
  61.  
  62.  
  63.  
  64.  
  65. static void producer()
  66. {
  67. for (size_t i = 0; i < N_GRAPHICS; i++)
  68. {
  69. auto g = new Graphic();
  70.  
  71. #ifdef CONCURRENT
  72. graphics.emplace_back(g);
  73. q.emplace(make_pair(g, i));
  74. #else
  75. if (g->parse())
  76. graphics.emplace_back(g);
  77. else
  78. delete g;
  79. #endif
  80. }
  81.  
  82. n_elements = graphics.size();
  83. }
  84.  
  85.  
  86.  
  87. static void consumer()
  88. {
  89. pair<Graphic*, size_t> item;
  90.  
  91. while (true)
  92. {
  93. {
  94. std::unique_lock<std::mutex> lk(m);
  95.  
  96. if (n_elements == 0)
  97. return;
  98.  
  99. n_elements--;
  100. item = q.front();
  101. q.pop();
  102. }
  103.  
  104. if (!item.first->parse())
  105. {
  106. assert(graphics[item.second].get() == item.first);
  107. delete item.first;
  108. graphics[item.second] = nullptr;
  109. }
  110. }
  111. }
  112.  
  113.  
  114.  
  115.  
  116. int main()
  117. {
  118. auto start = system_clock::now();
  119.  
  120. producer();
  121.  
  122. #ifdef CONCURRENT
  123.  
  124. vector<thread> threads;
  125.  
  126. for (auto i = 0; i < N_THREADS; i++)
  127. threads.emplace_back(consumer);
  128.  
  129. #endif
  130.  
  131. for (size_t i = 0; i < graphics.size(); i++)
  132. indexes.push_back(i);
  133.  
  134. #ifdef CONCURRENT
  135.  
  136. for (auto& t : threads)
  137. t.join();
  138.  
  139. #endif
  140.  
  141. auto duration = duration_cast<milliseconds>(system_clock::now() - start);
  142. cout << "Elapsed: " << duration.count() << endl;
  143.  
  144. for (size_t i = 0; i < graphics.size(); i++)
  145. {
  146. if (!graphics[i]->status)
  147. {
  148. cerr << "Assertion failed! (" << i << ")" << endl;
  149. break;
  150. }
  151. }
  152.  
  153. cin.get();
  154. return 0;
  155. }
Compilation error #stdin compilation error #stdout 0s 0KB
stdin
Standard input is empty
compilation info
/home/UgUvEh/ccsoRNh0.o: In function `void std::vector<std::thread, std::allocator<std::thread> >::_M_emplace_back_aux<void (&)()>(void (&)())':
prog.cpp:(.text._ZNSt6vectorISt6threadSaIS0_EE19_M_emplace_back_auxIIRFvvEEEEvDpOT_[_ZNSt6vectorISt6threadSaIS0_EE19_M_emplace_back_auxIIRFvvEEEEvDpOT_]+0x60): undefined reference to `pthread_create'
/home/UgUvEh/ccsoRNh0.o: In function `main':
prog.cpp:(.text.startup+0x14e): undefined reference to `pthread_create'
collect2: error: ld returned 1 exit status
stdout
Standard output is empty