私のアプリケーションでは、3つのクラス、、、がExtractor
ありTransformer
、Loader
これらは4番目のクラスで調整されていCoordinator
ます。Extractor
、Transformer
およびLoader
は非常に単純で、次のことを行います。
Extractor
たとえば、テキストファイルから読み取ることにより、Results
タイプと呼ばれるメンバーを公開します。IEnumerable<string>
抽出は同期する必要があります。
Transformer
Transform
文字列を受け入れ、時間がかかると予想されるプロセスを介して別の文字列に変換するというメンバーを公開します(ここでは並列処理を使用します)。
Loader
Load
文字列を受け入れ、それを最終的な形式(別のテキストファイルなど)にロードするというメンバーを公開します。読み込みは同期する必要があります。
Coordinator
クラスは3つの操作を調整します。変換プロセスは並行して実行する必要があり、次に結果をキューにプッシュして、ローダーによって読み取られます。Coordinator
のRun()
メソッドは次のようになります。
Extractor extractor = new Extractor();
Transformer transformer = new Transformer();
Loader loader = new Loader();
ConcurrentQueue<string> outputs = new ConcurrentQueue<string>();
Parallel.ForEach(extractor.Results, x => outputs.Enqueue(transformer.Transform(x)));
foreach(string output in outputs)
{
loader.Load(output);
}
これはうまく機能していますが、ロードを実行する前にすべての変換を終了する必要があります。つまりParallel.ForEach()
、次の開始前に完了しforeach
ます。準備ができ次第、各出力をローダーに渡すことをお勧めします。
私もこれを試しました:
Extractor extractor = new Extractor();
Transformer transformer = new Transformer();
Loader loader = new Loader();
ConcurrentQueue<string> outputs = new ConcurrentQueue<string>();
foreach (string input in extractor.Results)
{
string input1 = input;
Task task = Task.Factory.StartNew(
() => outputs.Enqueue(transformer.Transform(input1)));
}
foreach(string output in outputs)
{
loader.Load(output);
}
ただし、foreach
出力がキューに追加される前に下部のループがヒットするため、単に終了します。
の呼び出しから結果が利用可能になり次第、読み込みを実行するにはどうすればよいtransformer.Transform()
ですか?