在NET Framework 中在库的层次上微软提供了大量的新内容来帮助程序员完成应用程序的并行化其中包括Parallel LINQ(PLINQ)Task Parallel Library(TPL)和Coordination Data Structures这里我们就先来介绍一下最简单最常用的TPL
将跟随Visual Studio 一起发布的NET Framework 将包含很多基于库的对并行计算的支持包括数据的并行化任务的并行化等等这一切都通过一个共同的工作调度器进行管理这些新的类型和类将在SystemThreading SystemThreadingTasks SystemLinq 和 SystemCollectionsConcurrent这些名字空间中提供通过这些新的类型和类开发人员将无需面对如今复杂的多线程开发模式而可以直接使用NET Framework更加高效简便地开发支持并行计算的应用程序从而更加充分地利用多核CPU的优势随着计算核心或者处理器的增加以提升应用程序的性能
而在NET Framework中Task Parallel Library (TPL)是其Parallel Extensions中一个重要组成部分它提供了一种简便的多线程开发方式通过它所提供的类或者函数可以让程序员轻松地实现并行计算其中最简单的就是它的Parallel类
Parallel类
Parallel类就是TPL中的一个用于支持并行计算的类Parallel类提供了诸多的静态函数只需要简单的函数调用我们就可以对常用的for循环foreach循环进行并行化下面我们通过一些实际的例子来看看如何利用这个类将我们的应用程序并行化以吃上多核这免费的午餐
创建示例项目
为了演示如何将一个现有的项目并行化我们需要先创建一个示例项目在这个项目中我们将模拟对数据的串行操作然后介绍如何利用Parallel类将对数据的串行操作并行化以充分利用多核CPU的优势从而提升应用程序的性能
在Visual Studio 中我们新创建一个Visual C#的控制台应用程序然后在这个项目中添加一个类Employee其实现代码如下
using System;
using SystemCollectionsGeneric;
using SystemLinq;
using SystemText;
namespace ParallelDemo
{
// 职员类
public class Employee
{
public string FirstName
{
get;
set;
}
public string LastName
{
get;
set;
}
public string Address
{
get;
set;
}
public DateTime HireDate
{
get;
set;
}
public int EmployeeID
{
get;
set;
}
// 模拟对数据的处理
public static decimal Process(Employee employee)
{
ConsoleWriteLine(Processing {} employeeEmployeeID);
// 产生一个随机数
// 用以表示处理当前数据需要的时间
var rand = new Random(DateTimeNowMillisecond);
var delay = randNext( );
var count = ;
var process = true;
while (process)
{
SystemThreadingThreadSleep();
count++;
if (count >= delay)
process = false;
}
return delay;
}
}
// 职员列表类
// 这是我们需要处理的数据
public class EmployeeList : List
{
public EmployeeList()
{
// 将职员添加到列表中
Add(new Employee { EmployeeID = FirstName = 张 LastName = 三 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 李 LastName = 四 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 王 LastName = 麻子 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 赵 LastName = 匡胤 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 钱 LastName = 进 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 孙 LastName = 俊鹏 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 李 LastName = 明 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 周 LastName = 大勇 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 吴 LastName = 明子 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 郑 LastName = 邦万 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 王 LastName = 朝 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 冯 LastName = 玛丽 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 陈 LastName = 良乔 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 褚 LastName = 春晖 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 卫 LastName = 斯理 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 蒋 LastName = 中正 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 沈 LastName = 洋洋 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 韩 LastName = 斌 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 杨 LastName = 雪 HireDate = DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 朱 LastName = 辉 HireDate = DateTimeParse(//) });
DateTimeParse(//) });
Add(new Employee { EmployeeID = FirstName = 朱 LastName = 辉 HireDate = DateTimeParse(//) });
}
}
}
}
}
}