我的C#/ WPF应用程序中的TPL Dataflow网格出现问题。第一个输入项(称为“作业”)始终贯穿整个链,直到最后一个TPL块。但是,即使日志语句清楚地显示了已成功从第3块返回的作业,其余的作业也从未到达最后一个块(#4)。
这是网格。设置一次并存储在我的View-Model类的私有成员中。
// 1. _meshStartBlock: On UI thread. This block always works fine.
_meshStartBlock = new TransformBlock<Job, Job>(job =>
{
Jobs.Add(job);
Fire(_scanCapturedTrigger, job); // Notify sstate machine.
Log.Debug("Started: " + job.Name);
return job;
},
new ExecutionDataflowBlockOptions
{
CancellationToken = TokenSource.Token,
TaskScheduler = UiTaskScheduler // Run on UI thread (because it edits
// our ObservableCollection)
});
// 2. createBlock: This block also always works fine.
var createBlock = new TransformBlock<Job, Job>(job =>
{
job.CreateScan(); // Saves some disk files
job.CreateThumbnail(true); // Creates and saves a thumbnail image.
Log.Debug("Created: " + job.Name);
return job;
},
new ExecutionDataflowBlockOptions
{ CancellationToken = TokenSource.Token, MaxDegreeOfParallelism = 1 });
// 3. processBlock - do heavy work in parallel
// This block succeeds for all 3 jobs but 2nd and 3rd returned jobs never
// reach the next block.
var processBlock = new TransformBlock<Job, Job>(job =>
{
try
{
Log.Debug("Processing: " + job.Name);
job.AlignImages(); // heavy image processing
job.Generate3d(); // heavy 3d math
job.FindShapes(); // more heavy match
job.GetContext().Scan.Save(); // save disk files
Log.Debug("Processing succeeded: " + job.Name
}
catch (Exception e)
{
Log.Error("Processing failed: " + job.Name);
}
// *** THIS LOG STATEMENT SHOWS UP FOR ALL 3 JOBS ***
Log.Debug("Leaving process block: " + job.Name);
return job;
},
new ExecutionDataflowBlockOptions
{ CancellationToken = TokenSource.Token, MaxDegreeOfParallelism = 3 });
// 4. doneBlock: Cleans up.
// Since we schedule this on the UI thread it should not be heavy.
var doneBlock = new ActionBlock<Job>(job =>
{
// *** ONLY REACHED BY JOB 1 ***
Log.Debug("Done: " + job.Name);
Fire(Trigger.ScanProcessed); // Notify State Machine
},
new ExecutionDataflowBlockOptions
{ CancellationToken = TokenSource.Token, TaskScheduler = UiTaskScheduler });
// Set up the mesh. Link the blocks together to form a chain.
_meshStartBlock.LinkTo(createBlock);
createBlock.LinkTo(processBlock);
processBlock.LinkTo(doneBlock);
return _meshStartBlock;
这是我得到的日志输出
Started: Job1
Created: Job1
Started: Job2
Processing: Job1
Created: Job2
Processing: Job2
Started: Job3
Created: Job3
Processing: Job3
Processing succeeded: Job1
Leaving process block: Job1
Done: Job1
Processing succeeded: Job2
Leaving process block: Job2
Processing succeeded: Job3
Leaving process block: Job3
在处理或转储任何类型的错误消息期间,“调试”窗口不会报告任何异常。
我应该注意,我被迫在Release版本中运行它。如果我运行调试版本,则该过程块将花费数小时。而且从不调用CancellationToken
任何TPL-Dataflow专家都可以告诉我如何诊断Job2和Job3吗?无论如何,我可以得到TPL Dataflow来告诉我乔布斯发生了什么事吗?