Parallel.For 你可能忽视的一个非常实用的重载方法
下Parallel.For里面有14个重载,而其中那些比较复杂的重载方法,或许还有同学还不知道怎么用呢~~~ 刚好我最近我有应用场景了,给大家介绍介绍,废话不多说, 先给大家看一下这个并行方法的重载一览表吧。。。
? ? ?我遇到的场景是这样的,项目中有这样一个功能,这个功能需要根据多个维度对一组customerIDList进行筛选,最后求得多个维度所筛选出客户的并集,我举个 例子:现有8个维度:
每个维度都能筛选出一批customerid出来,然后对8组customerid求并集,这种场景很明显要提升性能的话,你必须要做并行处理,当然能够实现的方式有很多种, 比如我定义8个task Main( List<> rankList = Enum.GetNames(
Task
? ? ? 上面的代码的逻辑还是很简单的,我使用的是Task 插入,实现起来也是非常简单的,我就不演示了,那下面的问题来了,有没有更爽更直接的方式,看人家看上去更有档次一点的方法,而且还要达到这种效果呢?
?回到文章开头的话题,首先我们仔细分析一下下面这个复杂的重载方法。
ParallelLoopResult For
从上面的代码区域中看,你可以看到上面提供了5个参数,而最后意思的就是后面三个,如果你对linq的扩展方法比较熟悉的话,你会发现这个其实就是一个并行版本 的累加器(Aggregate)操作,因为他们都是具有三个区域:第一个区域就是初始化区域(localInit),就是累积之前的一个初始化操作,第二个区域其实就是一个迭代 区域,说白了就是foreach/for循环,for循环之中,会把计算结果累计到当初初始化区域设置的变量中,第三个区域就是foreach/for之后的一个最终计算区,三者合起 来就是一个并行累加器,为了方便大家更好的理解,我就扒一下源码给大家看看:
?由于图太大,就截两张图了,大家一定要仔细体会一下这里面的tlocal变量,因为这个tlocal的使用贯穿着三个区域,所以大家一定要好好体会下面这几句代码 TLocal tLocal =
tLocal =
(xxx< tLocal = localFinally(tLocal);
? ? ? 当你理解了tLocal具有累积foreach中的item结果之后,你就应该很明白下面这个body=>(item,loop,total) 和 finally =>?(total) 中total的含义了, 对吧,当你明白了,然后大家可以看看下面这段代码,是不是用一个方法就搞定了原来需要分阶段实现的一个业务逻辑呢? Main( List<> rankList = Enum.GetNames(
hashCustomerIDList = HashSet<>();
Parallel.For(,rankList.Count,() => { List<>(); },(item,total) =>
smallCustomerIDHash =
},(total) =>
( customerID
HashSet<> GetXXXMethod( HashSet<>
交易行为 = 营销活动 = 地区 = 新老客户 = 营销渠道 = 客户属性 = 客户分组 = 商品 =
}
? ?好了,本篇就先说这么多,希望这个具有并行累加器效果的Parallel.For能够给你带来一丝灵感~~~ (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |