public static void InvokePipe() { var cts = new CancellationTokenSource(); Task.Run(() => { if (Console.ReadKey().KeyChar == 'c') { cts.Cancel(); } }); var sourceArrays = new BlockingCollection <int> [CollectionsNumber]; for (int i = 0; i < sourceArrays.Length; i++) { sourceArrays[i] = new BlockingCollection <int>(Count); } var filter1 = new PipelineWorker <int, decimal>(sourceArrays, (n) => Convert.ToDecimal(n * 0.97), cts.Token, "filter1"); var filter2 = new PipelineWorker <decimal, string>(filter1.Output, (s) => String.Format("---{0}--", s), cts.Token, "filter2"); var filter3 = new PipelineWorker <string, string>(filter2.Output, (s) => Console.WriteLine("The final result is :{0} on thread id {1}", s, Thread.CurrentThread.ManagedThreadId), cts.Token, "filter3"); try { Parallel.Invoke( () => { Parallel.For(0, sourceArrays.Length * Count, (j, state) => { if (cts.Token.IsCancellationRequested) { state.Stop(); } int k = BlockingCollection <int> .TryAddToAny(sourceArrays, j); if (k >= 0) { Console.WriteLine("ADDed {0} to source data on thread id {1}", j, Thread.CurrentThread.ManagedThreadId); Thread.Sleep(TimeSpan.FromMilliseconds(100)); } }); foreach (var arr in sourceArrays) { arr.CompleteAdding(); } }, () => filter1.Run(), () => filter2.Run(), () => filter3.Run() ); }catch (AggregateException ex) { Console.WriteLine(ex); } if (cts.Token.IsCancellationRequested) { Console.WriteLine("operation has been can cancel"); } }
public override void Run() { var cts = new CancellationTokenSource(); Task.Run(() => { if (Console.ReadKey().KeyChar == 'c') { cts.Cancel(); } }, cts.Token); var sourceArrays = new BlockingCollection <int> [CollectionsNumber]; for (int i = 0; i < sourceArrays.Length; i++) { sourceArrays[i] = new BlockingCollection <int>(Count); } var convertToDecimal = new PipelineWorker <int, decimal>( sourceArrays, n => Convert.ToDecimal(n * 100), cts.Token, "Decimal Converter"); var stringifyNumber = new PipelineWorker <decimal, string>( convertToDecimal.Output, s => $"--{s.ToString("C", CultureInfo.GetCultureInfo("en-us"))}--", cts.Token, "String Formatter" ); var outputResultToConsole = new PipelineWorker <string, string>( stringifyNumber.Output, s => Console.WriteLine($"final result {s} thread id {Thread.CurrentThread.ManagedThreadId}"), cts.Token, "Console Output" ); try { Parallel.Invoke( () => CreateInitialValues(sourceArrays, cts), () => convertToDecimal.Run(), () => stringifyNumber.Run(), () => outputResultToConsole.Run()); } catch (AggregateException e) { foreach (var ex in e.InnerExceptions) { Console.WriteLine(ex.Message + ex.StackTrace); } } if (cts.Token.IsCancellationRequested) { Console.WriteLine("Operation has been canceled! Press ENTER to exit."); } else { Console.WriteLine("Press ENTER to exit."); } Console.ReadLine(); }
/// <summary> /// 使用BlockingCollection实现并行管道 /// </summary> /// <param name="args"></param> static void Main(string[] args) { var cts = new CancellationTokenSource(); // 监视c键(按下c键取消执行) Task.Run(() => { if (Console.ReadKey().KeyChar == 'c') { cts.Cancel(); } }, cts.Token); // 创建4个集合,每个集合中有5个元素 var sourceArrays = new BlockingCollection <int> [CollectionsNumber]; for (int i = 0; i < sourceArrays.Length; i++) { sourceArrays[i] = new BlockingCollection <int>(Count); } // 第一个管道:将int型数据转换成Decimal型 var convertToDecimal = new PipelineWorker <int, decimal>( sourceArrays, n => Convert.ToDecimal(n * 100), cts.Token, "Decimal Converter" ); // 第二个管道:格式化Decimal数据为金额字符串 var stringifyNumber = new PipelineWorker <decimal, string>( convertToDecimal.Output, s => $"--{s.ToString("C", CultureInfo.GetCultureInfo("en-us"))}--", cts.Token, "Console Formatter" ); // 第三个管道:打印格式化后的结果 var outputResultToConsole = new PipelineWorker <string, string>( stringifyNumber.Output, s => Console.WriteLine($"The final result is {s} on thread id {Thread.CurrentThread.ManagedThreadId}"), cts.Token, "Console Output" ); try { Parallel.Invoke( // 初始化集合数据 () => CreateInitialValues(sourceArrays, cts), // 将int型数据转换成Decimal型 () => convertToDecimal.Run(), // 格式化Decimal数据为金额字符串 () => stringifyNumber.Run(), // 打印格式化后的结果 () => outputResultToConsole.Run() ); } catch (AggregateException ae) { foreach (var ex in ae.InnerExceptions) { Console.WriteLine(ex.Message + ex.StackTrace); } } if (cts.Token.IsCancellationRequested) { Console.WriteLine("Operation has been canceled! Press ENTER to exit."); } else { Console.WriteLine("Press ENTER to exit."); } Console.ReadLine(); }
//并行管道模式以顺序阶段的方式处理元素 static void Main(string[] args) { var cts = new CancellationTokenSource(); Task.Run(() => { if (Console.ReadKey().KeyChar == 'c') { cts.Cancel(); } }); var sourceArrays = new BlockingCollection <int> [CollectionsNumber]; for (int i = 0; i < sourceArrays.Length; i++) { //将初始值放入到前四个集合中,其将被作为数据源被下一阶段使用 sourceArrays[i] = new BlockingCollection <int>(Count); } var filter1 = new PipelineWorker <int, decimal>(sourceArrays, i => Convert.ToDecimal(i * 0.97), cts.Token, "filter1"); var filter2 = new PipelineWorker <decimal, string>(filter1.Output, i => string.Format("--{0}--", i), cts.Token, "filter2"); var filter3 = new PipelineWorker <string, string>(filter2.Output, i => Console.WriteLine("最终结果 {0} 线程 id {1} ", i, Thread.CurrentThread.ManagedThreadId), cts.Token, "filter3"); try { Parallel.Invoke( () => { Parallel.For(0, sourceArrays.Length * Count, (j, state) => { if (cts.Token.IsCancellationRequested) { state.Stop(); } int k = BlockingCollection <int> .TryAddToAny(sourceArrays, j); if (k >= 0) { Console.WriteLine("加入 {0} 到源数据 线程id {1}", j, Thread.CurrentThread.ManagedThreadId); Thread.Sleep(TimeSpan.FromMilliseconds(100)); } }); foreach (var arr in sourceArrays) { arr.CompleteAdding(); } }, () => filter1.Run(), () => filter2.Run(), () => filter3.Run() ); } catch (AggregateException ae) { foreach (var ex in ae.InnerExceptions) { Console.WriteLine(ex.Message + ex.StackTrace); } } if (cts.Token.IsCancellationRequested) { Console.WriteLine("操作已经被取消! Press ENTER to exit."); } else { Console.WriteLine("Press ENTER to exit"); } Console.ReadLine(); }