|
|
|
|
|
|
|
|
|
|
|
#include <iostream> |
|
|
|
|
|
#include <vector> |
|
|
|
|
|
#include <string> |
|
|
|
|
|
#include <sstream> |
|
|
|
|
|
#include <cstdlib> |
|
|
|
|
|
#include "../CodeDweller/timing.hpp" |
|
|
|
|
|
#include "multitasking.hpp" |
|
|
|
|
|
|
|
|
|
|
|
using namespace std; |
|
|
|
|
|
|
|
|
|
|
|
class TaskHistory : public vector<string> { |
|
|
|
|
|
public: |
|
|
|
|
|
void post(string stuff) { |
|
|
|
|
|
push_back(stuff); |
|
|
|
|
|
} |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
string makeProgressMessage(int m) { |
|
|
|
|
|
stringstream messageBuilder; |
|
|
|
|
|
messageBuilder << "Making Progress (" << m << ")"; |
|
|
|
|
|
return messageBuilder.str(); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
class TestTask : public MultiTask { |
|
|
|
|
|
private: |
|
|
|
|
|
string myName; |
|
|
|
|
|
TaskHistory& myHistory; |
|
|
|
|
|
Timeout myReadyTimeout; |
|
|
|
|
|
|
|
|
|
|
|
MultiTaskState task() { |
|
|
|
|
|
if(false == myReadyTimeout.isExpired()) return Waiting; |
|
|
|
|
|
int myChangedMind = rand() % 100; |
|
|
|
|
|
MultiTaskState myNewState = Running; |
|
|
|
|
|
switch(myChangedMind) { |
|
|
|
|
|
case 0: { |
|
|
|
|
|
myHistory.post("I'm Finished!"); |
|
|
|
|
|
myNewState = Finished; |
|
|
|
|
|
break; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
case 1: |
|
|
|
|
|
case 3: |
|
|
|
|
|
case 5: |
|
|
|
|
|
case 51: |
|
|
|
|
|
case 53: |
|
|
|
|
|
case 55: |
|
|
|
|
|
case 71: |
|
|
|
|
|
case 73: |
|
|
|
|
|
case 75: |
|
|
|
|
|
case 9: { |
|
|
|
|
|
myHistory.post("I need a nap..."); |
|
|
|
|
|
myReadyTimeout.restart(); |
|
|
|
|
|
myNewState = Waiting; |
|
|
|
|
|
break; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
default: { |
|
|
|
|
|
myHistory.post(makeProgressMessage(myChangedMind)); |
|
|
|
|
|
myNewState = Running; |
|
|
|
|
|
break; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
return myNewState; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
static const int napDuration = 10; |
|
|
|
|
|
|
|
|
|
|
|
public: |
|
|
|
|
|
|
|
|
|
|
|
TestTask(string theName, TaskHistory& theHistory) : |
|
|
|
|
|
myName(theName), |
|
|
|
|
|
myHistory(theHistory), |
|
|
|
|
|
myReadyTimeout(napDuration) { |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
string name() { return myName; } |
|
|
|
|
|
|
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
void outputHistory(TaskHistory& H) { |
|
|
|
|
|
for(vector<string>::iterator s = H.begin(); s != H.end(); ++s) { |
|
|
|
|
|
cout << *s << endl; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
int main() { |
|
|
|
|
|
unsigned long seed = 1234; |
|
|
|
|
|
srand(seed); |
|
|
|
|
|
cout << "MultiTasker Demo! seed(" << seed << ")" << endl; |
|
|
|
|
|
|
|
|
|
|
|
TaskHistory H0, H1, H2, H3, H4, H5, H6, H7, H8, H9; |
|
|
|
|
|
TestTask T0("Random Job 0", H0); |
|
|
|
|
|
TestTask T1("Random Job 1", H1); |
|
|
|
|
|
TestTask T2("Random Job 2", H2); |
|
|
|
|
|
TestTask T3("Random Job 3", H3); |
|
|
|
|
|
TestTask T4("Random Job 4", H4); |
|
|
|
|
|
TestTask T5("Random Job 5", H5); |
|
|
|
|
|
TestTask T6("Random Job 6", H6); |
|
|
|
|
|
TestTask T7("Random Job 7", H7); |
|
|
|
|
|
TestTask T8("Random Job 8", H8); |
|
|
|
|
|
TestTask T9("Random Job 9", H9); |
|
|
|
|
|
|
|
|
|
|
|
MultiTasker M0; |
|
|
|
|
|
M0.put(T0); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T1); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T2); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T3); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T4); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T5); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T6); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T7); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T8); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
M0.put(T9); cout << "Pending Count: " << M0.pending() << endl; |
|
|
|
|
|
|
|
|
|
|
|
PollTimer NothingToDo(10,50); |
|
|
|
|
|
|
|
|
|
|
|
while(M0.hasWork()) { |
|
|
|
|
|
M0.task(); |
|
|
|
|
|
cout |
|
|
|
|
|
<< "In Work: " << M0.pending() |
|
|
|
|
|
<< ", Working: " << M0.working.size() |
|
|
|
|
|
<< ", Waiting: " << M0.waiting.size() |
|
|
|
|
|
<< ", Finished: " << M0.finished.size(); |
|
|
|
|
|
|
|
|
|
|
|
if(M0.isReady()) { |
|
|
|
|
|
cout << endl; |
|
|
|
|
|
NothingToDo.reset(); |
|
|
|
|
|
} |
|
|
|
|
|
else if(M0.isWaiting()) { |
|
|
|
|
|
cout << " pause..." << endl; |
|
|
|
|
|
NothingToDo.pause(); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "M0 Complete Order..." << endl; |
|
|
|
|
|
bool firstT = true; |
|
|
|
|
|
while(M0.canGet()) { |
|
|
|
|
|
TestTask& T = (TestTask&) M0.get(); |
|
|
|
|
|
if(firstT) { firstT = false; } |
|
|
|
|
|
else { cout << ", "; } |
|
|
|
|
|
cout << T.name(); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T0(" << T0.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H0); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T1(" << T1.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H1); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T2(" << T2.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H2); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T3(" << T3.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H3); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T4(" << T4.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H4); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T5(" << T5.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H5); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T6(" << T6.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H6); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T7(" << T7.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H7); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T8(" << T8.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H8); |
|
|
|
|
|
|
|
|
|
|
|
cout << endl << endl << "T9(" << T9.name() << ") History..." << endl; |
|
|
|
|
|
outputHistory(H9); |
|
|
|
|
|
|
|
|
|
|
|
return 0; |
|
|
|
|
|
} |
|
|
|
|
|
|