探究Visual Studio 2010中Parallel的使用(2) 軟件測試
對Parallel.Invoke進行控制
Parallel.Invoke提供了一個重載版本,它可以接受一個ParallelOptions對象作為參數,對Parallel.Invoke的執行進行控制。通過這個對象,我們可以控制并行的最大線程數,各個任務是否取消執行等等。例如,在一個智能化的家中,系統會判斷主人是否離開房間,如果主人離開了房間,則自動關閉屋子里的各種電器。利用Parallel.Invoke我們可以實現如下:
public static void PInvokeCancel() { // 創建取消對象 CancellationTokenSource cts = new CancellationTokenSource(); // 利用取消對象,創建ParallelOptions ParallelOptions pOption = new ParallelOptions() { CancellationToken = cts.Token }; // 設置最大線程數 pOption.MaxDegreeOfParallelism = 2; // 創建一個守護監視進程 Task.Factory.StartNew(() => { Console.WriteLine("Cancellation in 5 sec."); Thread.Sleep(5000); // 取消,結束任務的執行 cts.Cancel(); Console.WriteLine("Canceled requested"); }); try { // 以ParallelOptions作為參數, // 調用Parallel.Invoke Parallel.Invoke(pOption, () => ShutdownLights(pOption.CancellationToken), () => ShutdownComputer(pOption.CancellationToken)); //輸出執行結果 Console.WriteLine("Lights and computer are tuned off."); } catch (Exception e) { Console.WriteLine(e.Message); } } private static void ShutdownLights(CancellationToken token) { while (!token.IsCancellationRequested) { Console.WriteLine("Light is on. " ); Thread.Sleep(1000); } } private static void ShutdownComputer(CancellationToken token) { while (!token.IsCancellationRequested) { Console.WriteLine("Computer is on." ); Thread.Sleep(1000); } }
除了這種方式之外,ParallelOptions更多地應用在取消任務隊列中還未來得及執行的任務。當我們限制了最大并發線程數的時候,如果需要通過Parallel.Invoke執行的任務較多,則有可能部分任務在隊列中排隊而得不到及時的執行,如果到了一定的條件這些任務還沒有執行,我們可能取消這些任務。一個恰當的現實生活中的例子就是火車站買票?;疖囌举I票的人很多,但是售票的窗口有限,當到了下班時間后,窗口就不再售票了,也就是剩下的售票任務需要取消掉。我們可以用下面的代碼來模擬這樣一個場景:
public static void PInvokeCancel() { // 創建取消對象 CancellationTokenSource cts = new CancellationTokenSource(); // 利用取消對象,創建ParallelOptions ParallelOptions pOption = new ParallelOptions() { CancellationToken = cts.Token }; // 設置最大線程數,也就相當于20個售票窗口 pOption.MaxDegreeOfParallelism = 20; // 創建一個守護監視進程 // 當到下班時間后就取消剩下的售票活動 Task.Factory.StartNew(() => { Console.WriteLine("Cancellation in 5 sec."); Thread.Sleep(5000); // 取消,結束任務的執行 cts.Cancel(); Console.WriteLine("Canceled requested"); }); try { // 創建售票活動 Action[] CustomerServices = CreateCustomerService(1000); // 以ParallelOptions作為參數, // 調用Parallel.Invoke Parallel.Invoke(pOption, CustomerServices); } catch (Exception e) { // 當任務取消后,拋出一個異常 Console.WriteLine(e.Message); } } // 創建售票的活動 static Action[] CreateCustomerService(int n) { Action[] result = new Action[n]; for (int i = 0; i < n; i++) { result[i] = () => { Console.WriteLine("Customer Service {0}", Task.CurrentId); // 模擬售票需要的時間 Thread.Sleep(2000); }; } return result; }
原文轉自:http://www.anti-gravitydesign.com