.Net进阶系列(13)-异步多线程(Task和Parallel)(被替换)
2017-06-23 20:00
302 查看
[b]一. Task开启多线程的三种形式[/b]
1. 利用TaskFactory下的StartNew方法,向StartNew传递无参数的委托,或者是Action<object>委托。
2. 利用Task.Run()开启多线程,能向其中传递无参数的委托,有参数的可以使用 Task.Run(()=>{ TestThread("ypf") })这种形式。(推荐这种方式,最简洁。)
3. 先实例化Task,然后调用Start方法进行线程的开启。 Task构造函数可以无参委托或无参委托+object类型参数。 (同样道理,无参委托赋值有参函数,可以用之前的方案解决)
[b]二. 线程等待的两种形式[/b]
1. 利用Task下的静态方法WaitAll和WaitAny,来进行线程等待。(如果是主线程执行,则卡主主线程,如果新建一个子线程执行,则卡主了子线程)
2. 利用TaskFactory下的ContinueWhenAny和ContinueWhenAll,来进行线程等待。
[b]三. Parallel并行计算[/b]
1. 并行计算和多线程的区别:
多线程:如果要线程等待,需要单独开辟一个线程来进行线程等待,主线程在那等着。
并行计算:开启多个线程,默认就是线程等待,主线程在那等着,所以会卡主线程。
2. 并行计算的三种形式
Parallel.Invoke();
Parallel.For();
Parallel.ForEach()
1. 利用TaskFactory下的StartNew方法,向StartNew传递无参数的委托,或者是Action<object>委托。
2. 利用Task.Run()开启多线程,能向其中传递无参数的委托,有参数的可以使用 Task.Run(()=>{ TestThread("ypf") })这种形式。(推荐这种方式,最简洁。)
3. 先实例化Task,然后调用Start方法进行线程的开启。 Task构造函数可以无参委托或无参委托+object类型参数。 (同样道理,无参委托赋值有参函数,可以用之前的方案解决)
public static void Test4() { //一. 各种委托的赋值 //1. 无参数委托(包括方法有参数,如何赋值给无参委托) Action act1 = TestThread3; Action act2 = () => TestThread2("测试参数1"); Action act3 = () => TestThread("测试参数1", "测试参数2"); //2. 和方法参数对应的委托 Action act4 = () => TestThread3(); Action<string> act5 = t => TestThread2(t); Action<string, string> act6 = (m, n) => TestThread(m, n); //3. Action<object>委托 Action<object> act7 = t => TestThread3(); Action<object> act8 = t => TestThread2(t.ToString()); //多个参数的函数要用实例类的方法解决 //4. 委托赋值时不传参数,调用的时候传递 Action act9 = TestThread3; Action<string> act10 = TestThread2; Action<string, string> act11 = TestThread; //二. TaskFactory多线程的几种情况 TaskFactory taskFactory = new TaskFactory(); //1. 调用无参委托不需要传递参数 //{ // taskFactory.StartNew(act1); // taskFactory.StartNew(act2); // taskFactory.StartNew(act3); //} //2. 调用和方法参数对应的委托,需要在调用的时候传递参数 //{ // taskFactory.StartNew(act4); // taskFactory.StartNew(act5, "测试参数1"); //不支持(StartNew没有这种重载) // taskFactory.StartNew(act6, "测试参数1", "测试参数2"); //不支持(StartNew没有这种重载) //} //3. 调用Action<object>委托 //{ // taskFactory.StartNew(act7,""); // taskFactory.StartNew(act8, "测试参数1"); //} //4. 调用 委托赋值时不传参数,调用的时候传递 //{ // taskFactory.StartNew(act9); // taskFactory.StartNew(act10, "测试参数1"); //不支持(StartNew没有这种重载) // taskFactory.StartNew(act11, "测试参数1", "测试参数2"); //不支持(StartNew没有这种重载) //} //三. 使用Task.Run() 多线程的几种情况 //1. 调用无参委托不需要传递参数 //{ // Task.Run(act1); // Task.Run(act2); // Task.Run(act3); // Task.Run(act4); // Task.Run(act9); //} //除了上述五种方式,其他均不支持 //四. 利用Task实例下的Start方法开启多线程 //1.act1 act2 act3 act4 act9 调用无参委托不需要传递参数,均可以调用 //{ // Task task = new Task(act9); // task.Start(); //} //2. Action<object>委托可以使用 //act7和act8可以调用 { Task task = new Task(act7, ""); task.Start(); } { Task task = new Task(act8, "测试参数1"); task.Start(); } }
[b]二. 线程等待的两种形式[/b]
1. 利用Task下的静态方法WaitAll和WaitAny,来进行线程等待。(如果是主线程执行,则卡主主线程,如果新建一个子线程执行,则卡主了子线程)
2. 利用TaskFactory下的ContinueWhenAny和ContinueWhenAll,来进行线程等待。
[b]三. Parallel并行计算[/b]
1. 并行计算和多线程的区别:
多线程:如果要线程等待,需要单独开辟一个线程来进行线程等待,主线程在那等着。
并行计算:开启多个线程,默认就是线程等待,主线程在那等着,所以会卡主线程。
2. 并行计算的三种形式
Parallel.Invoke();
Parallel.For();
Parallel.ForEach()
private void button6_Click(object sender, EventArgs e) { Stopwatch watch = new Stopwatch(); watch.Start(); Console.WriteLine("----------------- 七.并行运算Parallel --------------------------"); Console.WriteLine("----------------- button1_Click 开始 主线程id为:{0} --------------------------", Thread.CurrentThread.ManagedThreadId); //下面的测试结果发现,主线程均被卡住 //并行计算和多线程相比的区别: 多线程执行后,需要单独再开辟一个线程等待,然后主线程在执行。 而并行计算,开启多个线程后,不需要再开辟线程等待,直接是主线程完成后续操作 #region 写法一 //{ // Parallel.Invoke(() => this.TestThread("bct1") // , () => this.TestThread("bct2") // , () => this.TestThread("bct3") // , () => this.TestThread("bct4") // , () => this.TestThread("bct5") // ); //} #endregion #region 写法二 //{ // //前两个参数之间的差,就为并行计算线程的个数 // Parallel.For(5, 10, t => // { // //这里的t分别为:5,6,7,8,9 五个数 // string name = string.Format("bct{0}", t); // this.TestThread(name); // }); //} #endregion #region 写法三 //{ // //数组里的个数,就为并行计算线程的个数 // Parallel.ForEach(new int[] { 3, 5, 44, 55, 100 }, t => // { // //这里的t分别为:3, 5, 44, 55, 100五个数 // string name = string.Format("bct{0}", t); // this.TestThread(name); // }); //} #endregion #region 写法四 { ParallelOptions po = new ParallelOptions() { MaxDegreeOfParallelism = 5 //表示最大线程数为5,后面即使配置超过5,也无效 }; Parallel.For(6, 15, po, (t, state) => { string name = string.Format("bct{0}", t); this.TestThread(name); //state.Break(); //退出单次循环(没看到实际作用) // state.Stop(); //退出全部循环(没看到实际作用) //return; }); } #endregion watch.Stop(); Console.WriteLine("----------------- button1_Click 结束 主线程id为:{0} 总耗时:{1}--------------------------", Thread.CurrentThread.ManagedThreadId, watch.ElapsedMilliseconds); }
相关文章推荐
- .Net进阶系列(11)-异步多线程(委托BeginInvoke)(被替换)
- .Net进阶系列(14)-异步多线程(async和await)(被替换)
- .Net进阶系列(12)-异步多线程(Thread和ThreadPool)(被替换)
- .Net进阶系列(15)-异步多线程(线程的特殊处理和深究委托赋值)(被替换)
- 构建多线程应用程序2 Parallel 并行类:Parallel.ForEach()、Task异步操作类:Task.Factory.StartNew()、并行LINQ查询: AsParallel()
- .NET 异步多线程,Thread,ThreadPool,Task,Parallel
- 第二十三节: EF性能篇(三)之基于开源组件 Z.EntityFrameWork.Plus.EF6解决EF性能问题 第四节:一些指令总结 定时调度系列之Quartz.Net详解 第十七节:易混淆的概念(静态和非静态、拆箱和装箱) 那些年我们一起追逐的多线程(Thread、ThreadPool、委托异步调用、Task/TaskFactory、Parallerl、async和await)
- NET 异步多线程,THREAD,THREADPOOL,TASK,PARALLEL
- 重新想象 Windows 8 Store Apps (44) - 多线程之异步编程: 经典和最新的异步编程模型, IAsyncInfo 与 Task 相互转换
- 异步方法的意义何在,Async和await以及Task的爱恨情仇,还有多线程那一家子。
- CUDA系列学习(四)Parallel Task类型 与 Memory Allocation
- CUDA系列学习(四)Parallel Task类型 与 Memory Allocation
- C# 使用 Task 替换 ThreadPool ,异步监测所有线程(任务)是否全部执行完毕
- Android菜鸟的成长笔记(13)——异步任务(Async Task)
- .Net进阶系列(10)-异步多线程综述(被替换)
- C#5.0之后推荐使用TPL(Task Parallel Libray 任务并行库) 和PLINQ(Parallel LINQ, 并行Linq). 其次是TAP(Task-based Asynchronous Pattern, 基于任务的异步模式)
- CUDA系列学习(四)Parallel Task类型 与 Memory Allocation
- .NET/C# 中使用Task类进行多线程和异步操作
- C# 多线程系列之异步回调(委托)
- 重新想象 Windows 8 Store Apps (43) - 多线程之任务: Task 基础, 多任务并行执行, 并行运算(Parallel)