在Parallel.ForEach()中调用外部方法是否有任何特殊规则或注意事项?我想确保避免任何古怪的多线程问题。请考虑以下Parallel.ForEach()例程:
public void GetGroupUsers()
{
Parallel.ForEach(
groups.ToList(),
new ParallelOptions() { MaxDegreeOfParallelism = Environment.ProcessorCount },
group =>
{
//get associated user id's by group name
userGuids = GetUserGuidsForGroup(1);
//if no group-users then continue
if (userGuids == null) return;
//update group user map
foreach (var userGuid in userGuids)
groupUserMap.Add(new KeyValuePair<Guid, Guid>(group.Key, userGuid));
});
}
private List<Guid> GetUserGuidsForGroup(int groupNumber)
{
var userGuids = new List<Guid>();
//do a repo lookup of user guids for the groupNumber parameter and add to list
return userGuids;
}
答案 0 :(得分:1)
在Parallel.ForEach()中调用外部方法是否有任何特殊规则或注意事项?
在编写简单的多线程应用程序时,规则/注意事项与您需要的相同。只是在这里线程是通过池配置的,而不是由用户创建的。当你调用.Net framework apis时,你仍然在调用外部/框架方法。在.Net框架api调用的情况下,您只需要确保每个线程都有自己的唯一对象来进行调用(因此线程安全)或共享对象在线程安全区域中进行方法调用。专注于Write调用(改变对象的状态)而不是Read调用。列举一些重要的:
Interlocked
,Lock
,Semaphore
,{{1}等构造创建线程安全区域,不要编写/更新共享/全局/静态变量}} mutex
/ ThreadLocal
这样的东西,要小心,因为这里要处理ThreadStatic
,这意味着同一个线程可以/将用于多次迭代,因此它会保留您可能不期望的本地状态,因此可能需要显式重置此类变量的状态。这通常会导致问题。number_of_threads != number_of_Elements
API不适合IO绑定调用,Parallel
是更好的选择