2

Qt 4.8 for Embedded Linux を使用して、特定のフォルダーとそのすべてのファイルを消去するために使用される、再帰的な非クラス メンバー関数を呼び出したいと考えています。

bool removeFiles(const QString & dirName, Interface::ProgressDialog* const poProgressDialog, qint32* const itemDeletedCounter)
{
    bool result = true;

    try
    {
        QDir dir(dirName);

        if (dir.exists(dirName))
        {
            Q_FOREACH (QFileInfo info, dir.entryInfoList(QDir::NoDotAndDotDot | QDir::System | QDir::Hidden  | QDir::AllDirs | QDir::Files, QDir::DirsFirst))
            {
    //            if (Q_UNLIKELY(poProgressDialog->wasCanceled()))
    //                break;

                if (info.isDir())
                    result = removeFiles(info.absoluteFilePath(),poProgressDialog,itemDeletedCounter);
                else
                {
                    result = QFile::remove(info.absoluteFilePath());

                    try
                    {
                        poProgressDialog->setValue(*itemDeletedCounter);
                    }
                    catch (...)
                    {
                        const QString strTemp = QString("Error in removeFiles::poProgressDialog->setValue(*itemDeletedCounter); !!!");

                        mDebugS(strTemp);
                        mLog(strTemp);
                    }

                    ++(*itemDeletedCounter);
    //                mDebugS(QString("%1").arg(itemDeletedCounter));
                }

                if (!result)
                    return result;
            }

            result = dir.rmdir(dirName);
        }
    }
    catch (...)
    {
        const QString strTemp = QString("General error in removeFiles");

        mDebugS(strTemp);
        mLog(strTemp);
    }

    return result;
}

(try-catch は忘れてください。それらは「デバッグ」用でした)

ご覧のとおり、この関数は QProgressDialog のようなクラスへのポインターと整数へのポインターの両方をパラメーターとして受け取ります。QProgressDialog のようなクラスは、削除操作の進行状況でインターフェイスを更新し、整数には削除されたファイルの実際の数が格納されます。

私が抱えている問題は、QtConcurrent::run を使用してこの関数を呼び出すと、セグメンテーション違反、アライメント トラップなどが常に発生することです。

concurrentResp = QtConcurrent::run(removeFiles, QString(DEFAULT_RECORD_DIR), poDialog, &itemCounter);

関数を直接呼び出しても同じことは起こらないので、おそらく関数や ProgressDialog クラスの問題ではないことがわかります。そして、これをより注意深くデバッグするためにアクセスできる GDB がありません (GDB と Python のおかげです)。

したがって、私の質問は基本的に次のとおりです。私は何を間違っていますか? そして、エラーなしでこれを行うにはどうすればよいですか?

追加情報:

  • 今のところ、ProgressDialog と整数の両方が .cpp ファイルでグローバルですが、それらはしばらく前にローカルであり、問​​題はすでに存在していました。
  • main() の最後の「return」関数でアプリを閉じるときにのみ、セグ フォールトが表示されることがあります。ただ、このままではクリア作業を終える前に問題が発生してしまいます。
4

3 に答える 3

3

GUI は、メイン スレッドからのみ更新できます。

別のスレッドからダイアログを更新しようとしています。

これを試して

QMetaObject::invokeMethod(poProgressDialog, "setValue",
                          Qt::AutoConnection,
                          Q_ARG(qint32, *itemDeletedCounter));

これの代わりに :

poProgressDialog->setValue(*itemDeletedCounter);
于 2015-06-09T18:19:08.287 に答える
1

最善のアプローチはQObject、そのようなタスクに対してそれぞれを作成することです。このようにして、反乱の問題のほとんどは、シグナルスロットメカニズムによって解決できます。また、UI を実際の作業から分離します (これは常に推奨されます)。

タスクの進行状況は、UI オブジェクトのそれぞれのスロットに接続するシグナルを発行することによって報告されます。

于 2015-06-09T20:41:52.363 に答える