#include #include #include #include #include #include #include #include #include #include #include #define foreach BOOST_FOREACH #define atomic BOOST_PERSISTENT_ATOMIC #define retry BOOST_PERSISTENT_RETRY using namespace std; using namespace boost; using namespace persistent; using namespace posix_time; struct account{ account(){} account(int account_nr) : account_nr(account_nr),balance(0){} int account_nr; int balance; template void serialize(Archive &ar,unsigned int){ ar & account_nr; ar & balance; } }; struct teller{ teller() : thr(boost::bind(&teller::run,this)){} void run(){ loc bank=loc::pinned(); while(!this_thread::interruption_requested()){ int amount=random() % 1000; int acc1=random() % bank->accounts.size(); int acc2=random() % bank->accounts.size(); atomic{ bank->accounts[acc1]->balance+=amount; bank->accounts[acc2]->balance-=amount; } retry; } } thread thr; }; struct bank{ vector > accounts; int overall_balance() const{ int tmp=0; foreach(shared_loc const &a,this->accounts){ tmp+=a->balance; } return tmp; } friend class boost::serialization::access; template void serialize(Archive &ar,unsigned int){ ar & accounts; } }; loc create_db(int nr_of_accounts){ transaction tx; loc mybank(new bank); for(int c=0;c acc(new account(c)); mybank->accounts.push_back(acc); } mybank.pin(); tx.commit(); return mybank; } int main(int argc,char **argv){ srand(time(0)); int nr_of_threads=10; int nr_of_accounts=200; if(argc > 1) nr_of_threads=lexical_cast(argv[1]); if(argc > 2) nr_of_accounts=lexical_cast(argv[2]); database db("bankingdb"); loc mybank=loc::pinned(); if(!loc::pinned()) mybank=create_db(nr_of_accounts); cerr << "overall balance before: " << mybank.read()->overall_balance() << endl; ptr_vector tellers; for(int c=0;coverall_balance() << endl; }