Evo primera koji racuna Fibonacijev niz tako sto nasledjuje
QThread:
Code (cpp):
#include <QCoreApplication>
#include <QThread>
#include <iostream>
#include <cstdlib>
using std::cout;
using std::endl;
// calculates Fibonacci array
class Thread : public QThread
{
private:
long prev1;
long prev2;
public:
Thread(long p1, long p2) : prev1(p1), prev2(p2)
{
}
void run()
{
while (true)
{
long n = this->prev1 + this->prev2;
cout << QThread::currentThreadId() << "::Run::run():n=" << n << endl;
this->prev1 = this->prev2;
this->prev2 = n;
Thread::usleep(100000);
}
}
};
// starts three threads
int main(int argc, char* argv[])
{
QCoreApplication app(argc, argv);
Thread t1(1, 1);
Thread t2(1, 1);
Thread t3(1, 1);
t1.start();
t2.start();
t3.start();
t1.wait();
t2.wait();
t3.wait();
return EXIT_SUCCESS;
}
Ovde tri niti svaka za sebe paralelno racunaju zasebne Fibonacijeve nizove.
Evo primera koji nasledjuje
QRunnable i koristi
QThreadPool umesto da rucno pravis niti:
Code (cpp):
#include <QCoreApplication>
#include <QRunnable>
#include <QThread>
#include <QThreadPool>
#include <iostream>
#include <cstdlib>
using std::cout;
using std::endl;
// calculates Fibonacci array, it is not thread-safe because 'prev1' and 'prev2' of the same object are shared among threads
class Run : public QRunnable
{
private:
long prev1;
long prev2;
public:
Run(long p1, long p2) : prev1(p1), prev2(p2)
{
}
void run()
{
// support executing the same runnable more than once
QThreadPool::globalInstance()->tryStart(this);
while (true)
{
long n = this->prev1 + this->prev2;
cout << QThread::currentThreadId() << "::Run::run():n=" << n << endl;
this->prev1 = this->prev2;
this->prev2 = n;
usleep(100000);
}
}
};
// starts two runnables, 'r1' is shared among two threads
int main(int argc, char* argv[])
{
QCoreApplication app(argc, argv);
cout << "global pool:active=" << QThreadPool::globalInstance()->activeThreadCount() << ",max=" << QThreadPool::globalInstance()->maxThreadCount() << endl;
Run* r1 = new Run(1, 1);
Run* r2 = new Run(1, 1);
QThreadPool::globalInstance()->start(r1);
QThreadPool::globalInstance()->start(r1);
QThreadPool::globalInstance()->start(r2);
return EXIT_SUCCESS;
}
Obrati paznju da drugi primer ne vodi racuna o sinhronizaciji izmedju niti. To znaci da se
r1 deli izmedju razlicitih niti, koje zato rade sa istim Fibonacijevim nizom sto dovodi do problema tj. netacnog racunanja Fibonacijevog niza.
r2 se koristi u jednoj niti i nema tih problema jer ne mora nista da se sinhronizuje.
Cim pohvatas kako se radi sa nitima, moraces da pogledas cemu sluze muteksi (
QMutex) koji sluze da resavaju ovakve probleme sinhronizacija.
Sveti Avgustin: "Dobar hrišćanin treba da se kloni matematičara i svih onih koji daju lažna proročanstva. Postoji opasnost da su matematičari već sklopili pakt sa Đavolom, da pomrače čovekov um i da ga okuju okovima pakla."