2018年8月19日 星期日

【C#】Exception handling while multi-threading

  1. static void Main(string[] args)
  2. {
  3. try
  4. {
  5. Task.Run(() =>
  6. {
  7. throw new Exception("occurs in task");
  8. });
  9. }
  10. catch (Exception ex)
  11. {
  12. Console.WriteLine(ex.Message);
  13. }
  14. Console.ReadLine();
  15. }
執行上述程式你會發現 cmd 沒寫 ex.Message,原因是 exception handling 是 per thread 的,也就是說在外緒發生的 exception 主緒 catch 不到

這有幾個解
1. 把 try catch 改包在裡面(這個最簡單)
  1. static void Main(string[] args)
  2. {
  3. Task.Run(() =>
  4. {
  5. try
  6. {
  7. throw new Exception("occurs in task");
  8. }
  9. catch (Exception ex)
  10. {
  11. Console.WriteLine(ex.Message);
  12. }
  13. });
  14. Console.ReadLine();
  15. }

2. 靠 TaskStatus 判斷執行結果並挖掘其中的錯誤
  1. var t = Task.Run(() =>
  2. {
  3. throw new Exception("occurs in task");
  4. })
  5. .ContinueWith((result) =>
  6. {
  7. if (result.Status == TaskStatus.Faulted)
  8. {
  9. foreach (var ex in result.Exception.InnerExceptions)
  10. {
  11. Console.WriteLine(ex.Message);
  12. }
  13. }
  14. });

3. 使用 await
  1. static void Main(string[] args)
  2. {
  3. FooAsync();
  4. Console.ReadLine();
  5. }
  6.  
  7. private static async Task FooAsync()
  8. {
  9. try
  10. {
  11. await Task.Run(() =>
  12. {
  13. throw new Exception("occurs in task");
  14. });
  15. }
  16. catch (Exception ex)
  17. {
  18. Console.WriteLine(ex.Message);
  19. }
  20. }

沒有留言:

張貼留言