C# 4.0 调用-异常处理
My code运行4函数向类填充信息(使用Invoke),例如:C# 4.0 调用-异常处理,c#-4.0,task-parallel-library,C# 4.0,Task Parallel Library,My code运行4函数向类填充信息(使用Invoke),例如: class Person { int Age; string name; long ID; bool isVegeterian public static Person GetPerson(int LocalID) { Person person; Parallel.Invoke(() => {GetAgeFromWebServiceX(per
class Person
{
int Age;
string name;
long ID;
bool isVegeterian
public static Person GetPerson(int LocalID)
{
Person person;
Parallel.Invoke(() => {GetAgeFromWebServiceX(person)},
() => {GetNameFromWebServiceY(person)},
() => {GetIDFromWebServiceZ(person)},
() =>
{
// connect to my database and get information if vegeterian (using LocalID)
....
if (!person.isVegetrian)
return null
....
});
}
}
我的问题是:如果他不是素食主义者,我不能返回null,但我希望能够停止所有线程,停止处理,只返回null。如何实现它?好吧,您可以从操作中抛出异常,在
GetPerson
中捕获aggregateeexception
(即在Parallel.Invoke
周围放置一个try/catch块),检查它是否是正确的异常类型,然后返回null
除了停止所有线程之外,它完成了所有任务。我认为,除非您开始使用取消令牌,否则您不太可能轻松停止已经在运行的任务。您可以通过保留一个布尔值来停止执行更多任务,以指示到目前为止是否有任何任务失败,并让每个任务在开始之前检查。。。这有点难看,但会管用的
我怀疑使用“完整”任务而不是Parallel.Invoke
会使这一切变得更加优雅。要尽早退出Parallel.Invoke
,您必须做三件事:
安排检测是否要在第一个操作之前退出的操作。然后它会被提前安排(可能是第一次,但这并不能保证),所以你会很快知道你是否想退出
当检测到错误并捕获Jon的回答所示的aggregateeexception
时引发异常
使用取消代币。然而,这只有在你有机会检查他们的财产时才有意义
您的代码将如下所示:
var cts = new CancellationTokenSource();
try
{
Parallel.Invoke(
new ParallelOptions { CancellationToken = cts.Token },
() =>
{
if (!person.IsVegetarian)
{
cts.Cancel();
throw new PersonIsNotVegetarianException();
}
},
() => { GetAgeFromWebServiceX(person, cts.Token) },
() => { GetNameFromWebServiceY(person, cts.Token) },
() => { GetIDFromWebServiceZ(person, cts.Token) }
);
}
catch (AggregateException e)
{
var cause = e.InnerExceptions[0];
// Check if cause is a PersonIsNotVegetarianException.
}
然而,正如我所说的,取消代币只有在您能够检查它们的情况下才有意义。因此,在GetAgeFromWebServiceX
中应该有机会检查取消令牌并提前退出,否则,将令牌传递给这些方法是没有意义的。您确实需要首先从数据库加载您的人员
?实际上,您的代码使用空值调用Web服务
如果你的逻辑真的是顺序的,那么按顺序去做,并且只并行地做有意义的事情