ReportBuilder
class. Each type of report uses its own class, inherited from ReportBuilder
. Reports should preferably be built in parallel threads.run()
method: class MyThread : public QThread { Q_OBJECT protected: void run(); }; void MyThread::run() { ... }
ReportBuilder
. Wrap for him: RBWorker
. class RBWorker : public QObject { Q_OBJECT private: ReportBuilder *rb; /* */ QStringList file_list; /* */ ReportType r_type; /* */ public: RBWorker(ReportType p_type ); ~RBWorker(); void setFileList(const QStringList &files) { file_list = files; } /* */ public slots: void process(); /* */ void stop(); /* */ signals: void finished(); /* */ }; RBWorker:: RBWorker (ReportType p_type) { rb = NULL; r_type = p_type; } RBWorker::~ RBWorker () { if (rb != NULL) { delete rb; } } void RBWorker::process() { if(file_list.count() == 0) { emit finished(); return; } switch (r_type) { case REPORT_A: { rb = new ReportBuilderA (); break; } case REPORT_B: { rb = new ReportBuilderB (); break; } case REPORT_C: { rb = new ReportBuilderC (); break; } default: emit finished(); return ; } } rb->buildToFile(file_list); /* buildToFile rb->stop() */ emit finished(); return ; } void RBWorker::stop() { if(rb != NULL) { rb->stop(); } return ; }
ReportBuilder
instance is created in the process(),
method process(),
and not in the RBWorker
constructor.Session
class tracks changes in files and starts building reports. class Session : public QObject { Q_OBJECT public: Session(QObject *parent, const QString &directory, const QVector<ReportType> &p_rt); ~Session(); void buildReports(); private: void addThread(ReportType r_type); void stopThreads(); QStringList files; QVector<ReportType> reports; // signals: void stopAll(); // };
addThread
void Session::addThread(ReportType r_type) { RBWorker* worker = new RBWorker(r_type); QThread* thread = new QThread; worker->setFileList(files); /* */ worker->moveToThread(thread); /* . : */ connect(thread, SIGNAL(started()), worker, SLOT(process())); /* … process(), , : */ connect(worker, SIGNAL(finished()), thread, SLOT(quit())); /* … , finished() , quit() : */ connect(this, SIGNAL(stopAll()), worker, SLOT(stop())); /* … Session , finished() : */ connect(worker, SIGNAL(finished()), worker, SLOT(deleteLater())); /* … : */ connect(thread, SIGNAL(finished()), thread, SLOT(deleteLater())); /* … , . . : */ thread->start(); /* , RBWorker::process(), ReportBuilder */ return ; } void Session::stopThreads() /* */ { emit stopAll(); /* RBWorker , quit() */ } void Session::buildReports() { stopThreads(); for(int i =0; i < reports.size(); ++i) { addThread(reports.at(i)); } return ; } void Session::~Session() { stopThreads(); /* */ … }
Source: https://habr.com/ru/post/150274/
All Articles