Task.Factory.StartNew和Task.Run

在系統中單開線程進行操做,常常用到Task,發現Task主要有如下兩種方法async

Task.Factory.StartNew(() => { });
    Task.Run(() => { });spa

初識不知其中區別,特地參考其餘文章已作總結https://www.mgenware.com/blog/?p=338線程

首先說明Task.UnWrap的基本使用code

這個擴展方法定義在TaskExtensions類型中,命名空間在System.Threading.Tasks。Unwrap會把嵌套的Task<Task>或者Task<Task<T>>的結果提取出來。blog

就像這樣,不用Unwrap的話:string

 1 static void Main(string[] args)
 2 {
 3     doo();
 4     Task.Delay(-1).Wait();
 5 }
 6 
 7 static async void doo()
 8 {
 9     //運行嵌套的Task
10     //Task返回Task<Task<string>>
11     //第一個await後result類型爲Task<string>
12     var result = await Task.Run<Task<string>>(() =>
13         {
14             var task = Task.Run<string>(() =>
15                 {
16                     Task.Delay(1000).Wait();
17                     return "Mgen";
18                 });
19             return task;
20         });
21 
22     //第二個await後纔會返回string
23     Console.WriteLine(await result);
24 }

使用Unwrap後,結果能夠直接從嵌套Task中提取出來:it

 1 static async void doo()
 2 {
 3     //運行嵌套的Task
 4     //Task返回Task<Task<string>>
 5     //await後類型爲Task<string>,Unwrap後result類型爲string
 6     var result = await Task.Run<Task<string>>(() =>
 7         {
 8             var task = Task.Run<string>(() =>
 9                 {
10                     Task.Delay(1000).Wait();
11                     return "Mgen";
12                 });
13             return task;
14         }).Unwrap();
15 
16     //不須要await,result已是string
17     Console.WriteLine(result);
18 }

簡單地講,Task.Factory.StartNew和Task.Run區別之一就有Task.Run會自動執行Unwrap操做,可是Task.Factory.StartNew不會,Task.Run就是Task.Factory.StartNew的更人性化封裝,而Task.Factory.StartNew則是原始的執行。io

經過代碼來驗證:class

1 var task1 = Task.Factory.StartNew(async () => "Mgen");
2 var task2 = Task.Run(async () => "Mgen");
3 
4 Console.WriteLine(task1.GetType());
5 Console.WriteLine(task2.GetType());

輸出擴展

1 System.Threading.Tasks.Task`1[System.Threading.Tasks.Task`1[System.String]]
2 System.Threading.Tasks.UnwrapPromise`1[System.String]

能夠看到

使用Task.Factory.StartNew會返回原始的Task<Task<string>>。可是Task.Run則會直接返回async Lambda的結果,中間的Unwrap操做會自動進行。

相關文章
相關標籤/搜索