ROOT logo

From $ROOTSYS/tutorials/thread/stressThreadPool.C

// Usage:
// root [0] .L stressThreadPool.C++
// root [1] stressThreadPool(10)   10 = numThreads

// STD
#include <iostream>
#include <iterator>
#include <vector>
#include <unistd.h>
// ThreadPool
#include "TThreadPool.h"
// ROOT
#include "TThread.h"

//=============================================================================
using namespace std;
//=============================================================================
const size_t g_sleeptime = 1; // in secs.
const size_t g_multTasks = 50;
//=============================================================================

enum EProc {start, clean};

class TTestTask: public TThreadPoolTaskImp<TTestTask, EProc> {
public:
   bool runTask(EProc /*_param*/) {
      m_tid = TThread::SelfId();
      sleep(g_sleeptime);
      return true;
   }
   unsigned long threadID() const {
      return m_tid;
   }

private:
   unsigned long m_tid;
};
ostream &operator<< (ostream &_stream, const TTestTask &_task)
{
   _stream << _task.threadID();
   return _stream;
}

//=============================================================================
void stressThreadPool(size_t _numThreads, bool _needDbg = false)
{
   size_t numTasks(_numThreads * g_multTasks);
   TThreadPool<TTestTask, EProc> threadPool(_numThreads, _needDbg);
   vector <TTestTask> tasksList(numTasks);
   for (size_t i = 0; i < numTasks; ++i) {
      threadPool.PushTask(tasksList[i], start);
   }
   threadPool.Stop(true);

   //    ostream_iterator<TTestTask> out_it( cout, "\n" );
   //    copy( tasksList.begin(), tasksList.end(),
   //          out_it );

   typedef map<unsigned long, size_t> counter_t;
   counter_t counter;
   {
      vector <TTestTask>::const_iterator iter = tasksList.begin();
      vector <TTestTask>::const_iterator iter_end = tasksList.end();
      for (; iter != iter_end; ++iter) {
         counter_t::iterator found = counter.find(iter->threadID());
         if (found == counter.end())
            counter.insert(counter_t::value_type(iter->threadID(), 1));
         else {
            found->second = found->second + 1;
         }
      }
   }

   cout << "\n************* RESULT ****************" << endl;

   counter_t::const_iterator iter = counter.begin();
   counter_t::const_iterator iter_end = counter.end();
   bool testOK=true;
   for (; iter != iter_end; ++iter) {
      cout << "Thread " << iter->first << " was used " << iter->second << " times\n";
      // each thread suppose to be used equal amount of time,
      // exactly (g_numTasks/g_numThreads) times
      if (iter->second != g_multTasks) 
         testOK = false;
   }

   cout << "ThreadPool: simple test - "<< (testOK? "OK": "Failed") << endl;
}
 stressThreadPool.C:1
 stressThreadPool.C:2
 stressThreadPool.C:3
 stressThreadPool.C:4
 stressThreadPool.C:5
 stressThreadPool.C:6
 stressThreadPool.C:7
 stressThreadPool.C:8
 stressThreadPool.C:9
 stressThreadPool.C:10
 stressThreadPool.C:11
 stressThreadPool.C:12
 stressThreadPool.C:13
 stressThreadPool.C:14
 stressThreadPool.C:15
 stressThreadPool.C:16
 stressThreadPool.C:17
 stressThreadPool.C:18
 stressThreadPool.C:19
 stressThreadPool.C:20
 stressThreadPool.C:21
 stressThreadPool.C:22
 stressThreadPool.C:23
 stressThreadPool.C:24
 stressThreadPool.C:25
 stressThreadPool.C:26
 stressThreadPool.C:27
 stressThreadPool.C:28
 stressThreadPool.C:29
 stressThreadPool.C:30
 stressThreadPool.C:31
 stressThreadPool.C:32
 stressThreadPool.C:33
 stressThreadPool.C:34
 stressThreadPool.C:35
 stressThreadPool.C:36
 stressThreadPool.C:37
 stressThreadPool.C:38
 stressThreadPool.C:39
 stressThreadPool.C:40
 stressThreadPool.C:41
 stressThreadPool.C:42
 stressThreadPool.C:43
 stressThreadPool.C:44
 stressThreadPool.C:45
 stressThreadPool.C:46
 stressThreadPool.C:47
 stressThreadPool.C:48
 stressThreadPool.C:49
 stressThreadPool.C:50
 stressThreadPool.C:51
 stressThreadPool.C:52
 stressThreadPool.C:53
 stressThreadPool.C:54
 stressThreadPool.C:55
 stressThreadPool.C:56
 stressThreadPool.C:57
 stressThreadPool.C:58
 stressThreadPool.C:59
 stressThreadPool.C:60
 stressThreadPool.C:61
 stressThreadPool.C:62
 stressThreadPool.C:63
 stressThreadPool.C:64
 stressThreadPool.C:65
 stressThreadPool.C:66
 stressThreadPool.C:67
 stressThreadPool.C:68
 stressThreadPool.C:69
 stressThreadPool.C:70
 stressThreadPool.C:71
 stressThreadPool.C:72
 stressThreadPool.C:73
 stressThreadPool.C:74
 stressThreadPool.C:75
 stressThreadPool.C:76
 stressThreadPool.C:77
 stressThreadPool.C:78
 stressThreadPool.C:79
 stressThreadPool.C:80
 stressThreadPool.C:81
 stressThreadPool.C:82
 stressThreadPool.C:83
 stressThreadPool.C:84
 stressThreadPool.C:85
 stressThreadPool.C:86
 stressThreadPool.C:87
 stressThreadPool.C:88
 stressThreadPool.C:89