任务线程中抛出的exception,未被UnobservedTaskException捕获

我无法理解TPL中如何处理exception。 以下代码应说明我的问题。

using System; using System.Collections.Generic; using System.Net; using System.Threading; using System.Threading.Tasks; namespace WebDLApp { class Program { static void Main(string[] args) { TaskScheduler.UnobservedTaskException += TaskScheduler_UnobservedTaskException; // Not catching exception List sites = new List{ "http://microsoft.com", "http://yahoo.com", "http://facebook.com", "http://amazon.com", "http://foooo", "http://aol.com", "http://ask.com", "http://wikipedia.org" }; List<Task> tasks = new List<Task>(); foreach (string site in sites) { tasks.Add(Task.Factory.StartNew((wsite) => { using (WebClient wc = new WebClient()) { wc.DownloadString((string)wsite); // Thrown here, always return (string)wsite; } }, site) ); } Task.WaitAll(tasks.ToArray()); // Can't catch here int counter = 1; foreach (var task in tasks) { Console.WriteLine(counter.ToString() + task.Result); // Can't catch here either counter++; } Console.ReadLine(); } static void TaskScheduler_UnobservedTaskException(object sender, UnobservedTaskExceptionEventArgs e) // Never called { Console.WriteLine(e.Exception.Message); e.SetObserved(); } } } 

根据我的理解,使用TaskScheduler.UnobservedTaskException事件对象是一种非常好的方法来帮助处理棘手的第三方库中的exception。 但是,exception似乎总是在Task中抛出。 看起来它似乎永远不会被TaskScheduler(或任何工具处理TaskExceptions)捕获。

为了简洁起见,我省略了可能的try / catch位置并用注释标记它们。

我期待TaskScheduler_UnobservedTaskException事件处理程序打印到控制台并观察exception。 但是,一旦执行到达任务的结果,就会从Task中抛出WebException。

这里(如何使用TaskScheduler.UnobservedTaskException处理exception?)是解释。 只需更换

 Task.WaitAll(tasks.ToArray()); // Can't catch here 

 Task.Factory.StartNew(() => { while (true) { Thread.Sleep(1000); GC.Collect(); } }); return; 

TaskScheduler_UnobservedTaskException查看消息