C++ Qt多线程

C++ Qt多线程,c++,qt,C++,Qt,我试图从文本文件中读取数据,并将令牌保存在运行在windows上的SQLite数据库中 文件大小约为300MB,问题是我还没有使用线程,应用程序崩溃并被“无响应”消息卡住 这是我的密码 QDir dir(ui->lineEdit->text()); if(dir.exists() && ui->lineEdit->text()!=""){ CreateTables(); dir.setFilter(QDir::Files | QDir::

我试图从文本文件中读取数据,并将令牌保存在运行在windows上的SQLite数据库中 文件大小约为300MB,问题是我还没有使用线程,应用程序崩溃并被“无响应”消息卡住 这是我的密码

QDir dir(ui->lineEdit->text());
if(dir.exists() && ui->lineEdit->text()!=""){
    CreateTables();

    dir.setFilter(QDir::Files | QDir::Hidden | QDir::NoSymLinks);
    dir.setSorting(QDir::Size | QDir::Reversed);

    QFileInfoList list = dir.entryInfoList();
    for (int i = 0; i < list.size(); ++i)  {
        QFileInfo fileInfo = list.at(i);
        QFile file(ui->lineEdit->text()+"/"+ fileInfo.fileName());

        if (file.open(QIODevice::ReadOnly | QIODevice::Text)) {
            QSqlQuery qrry;
            qrry.prepare( "INSERT INTO documents (path) VALUES ('"+ui->lineEdit->text()+"/"+ fileInfo.fileName()+"')" );
            qrry.exec();

            QString line;
            QTextStream in(&file);
            int lineCount=0;
            while (!in.atEnd()) {

                line = in.readLine();
                lineCount++;
                QRegExp rx("(\\ |\\,|\\.|\\:|\\t)"); 
                QStringList line_tokens = line.split(rx);

                for(int i=0;i<line_tokens.length();i++){
                    if(line_tokens[i].length()>3){
                        QSqlQuery qry;
                        qry.prepare( "INSERT INTO tokens (token,path,line) VALUES ('"+line_tokens[i]+"', '"+ui->lineEdit->text()+"/"+ fileInfo.fileName()+"','"+QString::number(lineCount)+"')" );
                        qry.exec();
                    }
                }
            }
        }
        else{
            QMessageBox::information(this,"File Read Error","Couldn't Open File, Please Make Sure That This File Is Accessable And Readable !");
        }
        std::cout << std::endl;
    }
}
else{
    QMessageBox::critical(this,"Directory choosen is Not Valid","Please Make Sure That You Have Choosen A Valid Directory!");
}
QDir目录(ui->lineEdit->text());
如果(目录存在()&&ui->lineEdit->text()!=“”){
CreateTables();
dir.setFilter(QDir::Files | QDir::Hidden | QDir::NoSymLinks);
定向排序(QDir::Size | QDir::Reversed);
QFileInfoList=dir.entryInfoList();
对于(int i=0;ilineEdit->text()+“/”+fileInfo.fileName());
if(file.open(QIODevice::ReadOnly | QIODevice::Text)){
qsqlqrry;
prepare(“插入到文档(路径)值(“+ui->lineEdit->text()+”/“+fileInfo.fileName()+”)”;
qrry.exec();
QString线;
文件中的QTextStream(&F);
int lineCount=0;
而(!in.atEnd()){
line=in.readLine();
lineCount++;
QRegExp rx(“(\\\\\,\\\.\\:\\\\\t)”;
QStringList line_令牌=行分割(rx);
对于(int i=0;i3){
qsqlqry;
qry.prepare(“插入到标记(标记、路径、行)值中”(“+line_标记[i]+”,“+ui->lineEdit->text()+”/“+fileInfo.fileName()+”,“+QString::number(lineCount)+“)”);
qry.exec();
}
}
}
}
否则{
信息(此“文件读取错误”,“无法打开文件,请确保此文件可访问且可读!”);
}
std::cout首先,您可以简单地…等待,直到它处理所有数据。如果您只运行此程序一次,就可以了

然后,您不应该向数据库生成这样的请求流。运行一个大的插入比运行许多小的插入要好得多。您可以使用
batch
执行

那么,可能没有理由尝试将写操作与Db并行。我认为,它足够聪明,可以有效地管理写操作


但它值得并行解析。这里的最佳解决方案是使用
QtConcurrent
框架。它正是为此类任务而设计的。

这是您希望使用线程的理想情况。线程将在后台完成所有工作,尽管处理数据仍需要时间,但您的GUI不会出现变化d或不响应

我不完全理解您的应用程序,但您可以编写一个线程来完成所有这些处理器密集型工作,或者甚至可以编写两个线程—一个读取文件,另一个用于数据库—但两个线程需要更大的努力来实现。我建议您首先使用一个线程,因为它更简单


您肯定想在这里使用线程,这将解决您的应用程序没有响应消息的问题,通常人们会将此消息解释为“它已崩溃”或“已挂起”,而应用程序主线程正忙于剥夺GUI的正常功能。

您的代码乱七八糟。我已尝试对其进行格式化,但似乎缺少某些部分,并且甚至不会格式化。你能编辑你的答案来澄清你所说的“折叠”是什么意思吗?并且,更详细地描述错误或性能问题…这是做文件解析的部分,不需要知道rest@AymanJitan至少发布一些可以编译的格式正确的代码。@Bart对不起,这是完整的代码