使用 Parallel.ForEach<T> 设置 Parallel.ForEach 外部的布尔值
Using Parallel.ForEach<T> to set a bool external to Parallel.ForEach
我想在 List<T>
上使用 Parallel.ForEach
的强大功能进行验证。迭代列表以确保 属性 不 < 1。如果验证发现在验证方法调用中返回的错误,则会创建一个设置为 false 的布尔值。有人告诉我这段代码是有问题的,因为 bool 是原始的并且不是线程安全的。有没有一种方法可以在具有大量内核和 RAM 的服务器上利用 Parallel.ForEach
的强大功能,并确保它在线程安全方面正常工作?
public static bool IsValid(List<Airport> entities)
{
bool isValid = true;
Parallel.ForEach<Airport>(entities, entity =>
{
// userId can't be less than 1
if (entity.userId < 1)
{
SiAuto.Main.LogMessage("Airport {0}: invalid userId {1}", entity.airportId, entity.userId);
isValid = false;
System.Diagnostics.Debugger.Break();
}
});
return isValid;
}
如果列表足够大,我会使用 Enumerable.Any
或 Enumerable.All
:
的 PLINQ 方法
return !entities.AsParallel().Any(x => x.UserId < 1);
或
return entities.AsParallel().All(x => !(x.UserId < 1));
通常当使用管道式执行时,我发现 PLINQ 比 Parallel
class 更合适,因为它消除了在并行循环内更新共享资源的需要。
请注意,您应该对代码进行基准测试以确保并行性是值得的。在许多情况下,如果列表不够大,这可能会降低性能。
您可以使用 PLINQ 做到这一点:
public static bool IsValid(List<Airport> entities)
{
return !entities.AsParallel().Any(entity => entity.UserId < 1);
}
但是,由于并行部分 运行 太小,您不会得到任何改进,因此您应该坚持使用常规 foreach
(或 LINQ):
public static bool IsValid(List<Airport> entities)
{
return !entities.Any(entity => entity.UserId < 1);
}
我想在 List<T>
上使用 Parallel.ForEach
的强大功能进行验证。迭代列表以确保 属性 不 < 1。如果验证发现在验证方法调用中返回的错误,则会创建一个设置为 false 的布尔值。有人告诉我这段代码是有问题的,因为 bool 是原始的并且不是线程安全的。有没有一种方法可以在具有大量内核和 RAM 的服务器上利用 Parallel.ForEach
的强大功能,并确保它在线程安全方面正常工作?
public static bool IsValid(List<Airport> entities)
{
bool isValid = true;
Parallel.ForEach<Airport>(entities, entity =>
{
// userId can't be less than 1
if (entity.userId < 1)
{
SiAuto.Main.LogMessage("Airport {0}: invalid userId {1}", entity.airportId, entity.userId);
isValid = false;
System.Diagnostics.Debugger.Break();
}
});
return isValid;
}
如果列表足够大,我会使用 Enumerable.Any
或 Enumerable.All
:
return !entities.AsParallel().Any(x => x.UserId < 1);
或
return entities.AsParallel().All(x => !(x.UserId < 1));
通常当使用管道式执行时,我发现 PLINQ 比 Parallel
class 更合适,因为它消除了在并行循环内更新共享资源的需要。
请注意,您应该对代码进行基准测试以确保并行性是值得的。在许多情况下,如果列表不够大,这可能会降低性能。
您可以使用 PLINQ 做到这一点:
public static bool IsValid(List<Airport> entities)
{
return !entities.AsParallel().Any(entity => entity.UserId < 1);
}
但是,由于并行部分 运行 太小,您不会得到任何改进,因此您应该坚持使用常规 foreach
(或 LINQ):
public static bool IsValid(List<Airport> entities)
{
return !entities.Any(entity => entity.UserId < 1);
}