博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
多线程(7)多线程中的异常处理
阅读量:7238 次
发布时间:2019-06-29

本文共 3094 字,大约阅读时间需要 10 分钟。

  多线程使用过程中,除了线程同步的问题要考虑外,异常处理也是经常要面对的事情。

默认主线程捕获不到异步线程的异常

如下代码:

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 }
View Code

常用的异常处理方法

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                 try12                 {13                     throw new Exception("异步线和发生异常了!");14                 }15                 catch (Exception ex)16                 {17                     Console.WriteLine(ex.ToString());18                 }19             });20 21             Console.ReadKey();22         }23     }24 }
View Code

 运行结果:

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             try10             {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 }
View Code

 

运行结果:

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 }
View Code

 

运行结果:

 4,全局设置TaskScheduler.UnobservedTaskException

 如果异步线程里的异常没有被处理,也没有调用Task.Wait方法将异常传给主线程处理,最严重的后果可能会导致整个应用程序奔溃。详细原因参考:

所以,为了保证应用程序不会因为异步线程的异常未被处理导致挂掉,推荐的做法是,全局设置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 }
View Code

 

转载地址:http://eqrfm.baihongyu.com/

你可能感兴趣的文章
Android setRequestedOrientation用法
查看>>
面向对象三大基本特性,五大基本原则
查看>>
更改窗口图标并将其显示在任务栏
查看>>
包含的语句
查看>>
正则表达式-匹配标点符号
查看>>
osworkflow descriptor 解析 重要概念
查看>>
Edmonds_Karp 算法 (转)
查看>>
第一节 接口概述 [转贴]
查看>>
C# Attribute 用法备忘
查看>>
数据结构学习笔记(5.线性表之双向循环链表)
查看>>
智能家居趋势
查看>>
[Leetcode] Pow(x, n)
查看>>
关于Microsoft Speech SDK 中TTS的研究 [转]
查看>>
两个与后台有关的回调处理
查看>>
idhttp.post方式 调用datasnap rest 远程方法
查看>>
Gulp快速入门
查看>>
TClientDataSet的 fastscript封装
查看>>
有用的国外开源项目网址
查看>>
DataGridView 绑定DataTable方式编辑保存的bug?
查看>>
ComboBox 使用数据绑定时 Sorted 属性的bug
查看>>