从第一台计算机问世到现在计算机硬件技术已经有了很大的发展。不管是现在个人使用的PC还是公司使用的服务器。双核,四核,八核的CPU已经非常常见。这样我们可以将我们程序分摊到多个计算机CPU中去计算,在过去并行化需要线程的低级操作,难度很大,在.net4.0中的增强了对并行化的支持,使得这一切变得非常简单 。本次我从以下几个方面大家讲以下.NET 并行
本次主要给大家讲一下数据并行 废话不说,下面开始了
数据并行其实就是指对原集合或者数组中的数据进行划区之后分摊到多个CPU或者多个线程执行相同的操作 在 .net中的 System.Threading.Tasks 提供了对数据并行的支持类 , Parallel.For,Parallel.ForEach和我们经常的使用的for 和foreach 十分的相似,你不用创建线程队列,在基本的循环中你不用使用锁。这些.net 会帮你处理,你只需要关注你自己的业务 那下面我们就来看看 Parallel.For 和 Parallel.ForEach 是如何使用的
Parallel.For(0, 100, i => { dosameting() });
上面的例子是不是和我们经常使用的for循环的影子。 说一下 Parallel.For 的第三个参数class="code">Action<int>类型的委托 不管这个委托的参数是0个还是多少个他的返回植都是void,那么怎么样才能获取到Parallel.For 中的的返回值了,下面的例子将演示如何使用线程本地变量来存储和检索由 for 循环创建的每个单独任务中的状态 thread-local data, you can avoid the overhead of synchronizing a large number of accesses to shared state." data-guid="17abec43aa08e0ef5960e1c0fc465d83">通过使用线程本地数据,您可以避免将大量的访问同步为共享状态的开销。 在任务的所有迭代完成之前,您将计算和存储值,而不是写入每个迭代上的共享资源。 然后,您可以将最终结果一次性写入共享资源,或将其传递到另一个方法
Parallel.For<long>(0, listLength, () => 0, (j, loop, subsum) => { subsum += lista[j]; return subsum; }, (x) => Interlocked.Add(ref sum, x));
Parallel.For<long>(0, listLength, () => 0, (j, loop, subsum) => { if (subsum > 20000) { loop.Break(); } subsum += lista[j]; return subsum; }, (x) => Interlocked.Add(ref sum, x));
Parallel.ForEach(lista, i => { dosameting(); });
不知道大家在这个地方有没有看到foreach的影子。其实上面的例子中的ForEach方法的最后一个输入参数是 Action<int>委托,当所有循环完成时,方法将调用该委托。这个地方和前面的Parallel.For 是一样的。那么我们要如何获得返回值了和上面的For是非常相似,我依然以上面数组求和为例
Parallel.ForEach<int, long>(lista, () => 0, (j, loop, subsum) => { if (subsum > 20000) { loop.Break(); } subsum += lista[j]; return subsum; }, (x) => Interlocked.Add(ref sum, x));
欢迎大家拍砖