多线程(7)多线程中的异常处理
2018-06-18 04:12:19来源:未知 阅读 ()
多线程使用过程中,除了线程同步的问题要考虑外,异常处理也是经常要面对的事情。
默认主线程捕获不到异步线程的异常
如下代码:
1 namespace ConsoleApplication29 2 { 3 class Program 4 { 5 static void Main(string[] args) 6 { 7 //异步线程的异常处理 8 try 9 { 10 Task.Factory.StartNew(() => 11 { 12 throw new Exception("异步线和发生异常了!"); 13 }); 14 } 15 catch (Exception ex) 16 { 17 //这里是捕获不到的 18 Console.WriteLine(ex.ToString()); 19 } 20 21 Console.ReadKey(); 22 } 23 } 24 }
常用的异常处理方法
1,在异步线程内部使用try/catch
如下代码:
1 namespace ConsoleApplication29 2 { 3 class Program 4 { 5 static void Main(string[] args) 6 { 7 //异步线程的异常处理 8 //1,在异步线程内部使用try/catch 9 Task.Factory.StartNew(() => 10 { 11 try 12 { 13 throw new Exception("异步线和发生异常了!"); 14 } 15 catch (Exception ex) 16 { 17 Console.WriteLine(ex.ToString()); 18 } 19 }); 20 21 Console.ReadKey(); 22 } 23 } 24 }
运行结果:
2,调用Task的Wait方法
如下代码:
注意:
除了调用Task的Wait方法后,在主线程可以捕获异常外,对于有返回值的Task,只要接收了它的返回值就不再需要调用Wait方法了。
1 namespace ConsoleApplication29 2 { 3 class Program 4 { 5 static void Main(string[] args) 6 { 7 //异步线程的异常处理 8 //2,调用Task的Wait方法 9 try 10 { 11 var task = Task.Factory.StartNew(() => 12 { 13 throw new Exception("异步线和发生异常了!"); 14 }); 15 task.Wait(); 16 } 17 catch (Exception ex) 18 { 19 Console.WriteLine(ex.ToString()); 20 } 21 22 Console.ReadKey(); 23 } 24 } 25 }
运行结果:
3,在Task的ContinueWith方法中读取Task的Exception属性
如下代码:
1 namespace ConsoleApplication29 2 { 3 class Program 4 { 5 static void Main(string[] args) 6 { 7 //异步线程的异常处理 8 //3,在Task的ContinueWith方法中读取Task的Exception属性 9 Task.Factory.StartNew(() => 10 { 11 throw new Exception("异步线和发生异常了!"); 12 }).ContinueWith(t => 13 { 14 if (t.IsFaulted) 15 { 16 Console.WriteLine(t.Exception.InnerException); 17 } 18 }, TaskContinuationOptions.OnlyOnFaulted); 19 20 Console.ReadKey(); 21 } 22 } 23 }
运行结果:
4,全局设置TaskScheduler.UnobservedTaskException
如果异步线程里的异常没有被处理,也没有调用Task.Wait方法将异常传给主线程处理,最严重的后果可能会导致整个应用程序奔溃。详细原因参考:System.Threading.Tasks.Task引起的IIS应用程序池崩溃
所以,为了保证应用程序不会因为异步线程的异常未被处理导致挂掉,推荐的做法是,全局设置TaskScheduler.UnobservedTaskException。
如果是web程序,可以在Global的Application_Start事件中进行设置,如下代码:
1 protected override void Application_Start(object sender, EventArgs e) 2 { 3 System.Threading.Tasks.TaskScheduler.UnobservedTaskException += (s, v) => 4 { 5 v.SetObserved(); 6 }; 7 }
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
- MyBatis中的$和#,用不好,准备走人! 2020-06-11
- 构造函数中的this()和super() 2020-06-10
- 怎么用Java 高效提取、替换、删除PDF文档中的图片 2020-06-09
- Java笔记:数组,异常,泛型 2020-06-08
- 最详细的java多线程教程来了 2020-06-08
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash