0

したがって、いくつかのファイルを含むフォルダーがあります。各ファイルを通過し、それをスレッドに追加してバックグラウンドで処理するループがあり、UI が応答します。問題は、特定の時間に実行するスレッドを 1 つだけにしたいということです。したがって、基本的にはスレッドを「キューに入れ」、スレッドが完了すると次のスレッドを起動したいと考えています。これを行う最良の方法は何ですか?これが私が使用しているコードです。タイマーが最善の解決策であるかどうか疑問に思っていますか? みんな、ありがとう。

foreach (CustomerFile f in CF)
{
    btnGo.Enabled = false;
    UpdateProgressDelegate showProgress = new UpdateProgressDelegate(UpdateProgress);
    ProcessFile pf = new ProcessFile(this, showProgress, f._FileName, txtDestFolder.Text);
    Thread t = new Thread(new ThreadStart(pf.DoWork));
    t.IsBackground = true; 
    t.Start();
}
4

4 に答える 4

2

ファイルをキューに追加して、別のスレッドでキューを処理するのはどうですか?

Queue<CustomerFile> files = new Queue<CustomerFile>()
foreach (CustomerFile f in CF)
  files.Enqueue(f);

BackgroundWorker bwk = new BackgroundWorker();
bwk.DoWork+=()=>{
    //Process the queue here
    // if you update the UI don't forget to call that on the UI thread
};

bwk.RunWorkerAsync();
于 2013-01-15T14:47:16.700 に答える
1

これはプロデューサー/コンシューマー モデルであり、非常に一般的な要件です。C# ではBlockingCollection、このタスクに最適です。プロデューサーにそのコレクションに項目を追加してもらい、バックグラウンド タスク (任意の数の項目を含めることができます) にそのコレクションから項目を取得させます。

于 2013-01-15T14:50:53.247 に答える
1

キューを処理するバックグラウンド スレッドを1 つだけ使用するだけで済むようです。このようなもの:

var q = new Queue();
foreach (var file in Directory.GetFiles("path"))
{
    q.Enqueue(file);
}

var t = new Task(() =>
    {
        while (q.Count > 0)
        {
            ProcessFile(q.Dequeue());
        }
    });
t.Start();

これは、バックグラウンド スレッドがキューを処理している間にキューを変更する必要がない場合にのみ適切であることに注意してください。そうであれば、Servy の答えは正しいです。これは、消費者が 1 つしかない、ごく標準的な生産者と消費者の問題です。プロデューサー/コンシューマーの問題を解決する方法の詳細については、アルバハリのC# でのスレッド化 を参照してください。

于 2013-01-15T14:51:33.780 に答える
0

あなたがしなければならない唯一のことは、例えば次のようなスレッドにあなたのループを置くことです:

new Thread(()=>{
foreach (CustomerFile f in CF)
{
    btnGo.Enabled = false;
    UpdateProgressDelegate showProgress = new UpdateProgressDelegate(UpdateProgress);
    ProcessFile pf = new ProcessFile(this, showProgress, f._FileName, txtDestFolder.Text);
    pf.DoWork();

}
}).Start();
于 2013-01-15T17:27:59.007 に答える