オブジェクトを初期化するタスクがありますが、これはかなり長いです。それについて行く正しい方法は何ですか?
ここに私がこれまでに持っているコードがあります(簡単にするために、初期化は文字列リストへのエントリの追加のみで構成されています):
#ifndef TASKINITIALIZER_H
#define TASKINITIALIZER_H
#include <QDir>
#include <QThread>
#include <QObject>
#include "task.h"
class TaskInitializer:public QThread
{
Q_OBJECT
QDir dir;
QString msg;
Task &result;
public:
TaskInitializer(QString dname, bool png, bool jpg, bool bmp, Task &res);
~TaskInitializer();
const QString& getMessage();
bool isOk();
private:
void run();
};
#endif // TASKINITIALIZER_H
#include <QDir>
#include <QDirIterator>
#include "taskinitializer.h"
TaskInitializer::TaskInitializer(QString dname, bool png, bool jpg, bool bmp, Task & res):
dir(dname),result(res)
{
QStringList filters;
if (png)
filters << "*.png";
if(jpg)
{
filters << "*.jpeg" << "*.jpg";
}
if(bmp)
filters << "*.bmp";
dir.setNameFilters(filters);
}
TaskInitializer::~TaskInitializer()
{
}
const QString &TaskInitializer::getMessage()
{
return msg;
}
bool TaskInitializer::isOk()
{
if (!dir.exists())
{
msg = ("Directory does not exist");
return false;
}
if (dir.nameFilters().length() < 1)
{
msg = ("No image types chosen");
return false;
}
return true;
}
void TaskInitializer::run()
{
QDirIterator di(dir,QDirIterator::Subdirectories);
while(di.hasNext())
{
result.addFilename(di.next());
}
}
アイデアは、コンストラクターの初期化インスタンスにパラメーターを渡し、それらの有効性を確認してから、初期化自体を実行することです。ただし、初期化に時間がかかり、アプリケーションが突然停止する場合があります。この場合、イニシャライザはそのアクティビティを適切に停止し、クリーンアップする必要があります。
非同期タスクを実行するいくつかの方法を読みましたが、停止信号を検出する方法をまだ理解していません。私が見る限り、スレッドプールで QRunnable を実行したり、 QtConcurrent::run() を使用したりしても、停止する時間かどうかを確認するメカニズムはありません。
また、クリーンアップが保証されるように、適切に初期化されているオブジェクトを初期化タスクとの間で渡す方法について混乱しています。イニシャライザと同じです。クリーンアップされることをどのように保証できますか?
初期化を開始するために現在使用しているコードは次のとおりです。
_temp = new Task();
TaskInitializer *worker = new TaskInitializer(_directoryName,flags[2],flags[1],flags[0],*_temp);
if (!worker->isOk())
{
delete _temp;
_temp = NULL;
emit logMessage(worker->getMessage());
return _temp;
}
//clearTempTask();
emit logMessage("New task created");
connect(worker,SIGNAL(finished()),SIGNAL(taskInitialized()));
connect(worker,SIGNAL(finished()),worker,SLOT(deleteLater()));
worker->start();
worker = NULL;