任務Task與線程Thread不可比。Task是為了利用多CPU多核的機制而將一個大任務不斷分解成小任務,這些任務具體由哪一個線程或當前線程執行由OS來決定。如果你想自己控制由哪一個Thread執行,要么自己定議task的scheduling, 要么自己來創建Thread來執行代碼。
1)task是根據自己需要調用線程
2)thread就是個基本單位
簡單地du說,thread是單核多線程,task是多核多線程
/// <summary>
/// 簡單的task創建方式演示
/// </summary>
private static void TaskCreatFun()
{
// 其一、通過傳統的 new 方式來實例化一個task對象,這種方式需要手動通過start來啟動
Task newTask = new Task(() =>
{
Thread.Sleep(1000);
Console.WriteLine($"Hello Engineer, 我是 new 的一個task,線程ID:Thread.CurrentThread.ManagedThreadId}");
});
// 啟動 tsak
newTask.Start();
// 其二、通過工廠 factory 來生成一個task對象,並自啟動
Task factoryTask = Task.Factory.StartNew(() =>
{
Thread.Sleep(1000);
Console.WriteLine($"Hello Engineer, 我是 factory 生產 的一個task,線程ID:Thread.CurrentThread.ManagedThreadId}");
});
// 其三、通過 Task.Run(Action action) 來創建一個自啟動task
Task runTask = Task.Run(() =>
{
Thread.Sleep(1000);
Console.WriteLine($"Hello Engineer, 我是 Task.Run 創建一個自啟動task,線程ID:Thread.CurrentThread.ManagedThreadId}");
});
runTask.RunSynchronously();
Console.WriteLine($"Hello Engineer, 我是主線程啦!線程ID{Thread.CurrentThread.ManagedThreadId}");
}
Task回調
a.某一個任務結束回調
taskList.Add(taskFactory.StartNew(() => this.DoSomethingLong("btnTask_Click_002")));
taskList.Add(taskFactory.StartNew(() => this.DoSomethingLong("btnTask_Click_001")));
//回調ContinueWhenAny沒有那么精准,不一定是在某個線程完成之后發生
taskList.Add(taskFactory.ContinueWhenAny(taskList.ToArray(), t => Console.WriteLine($"ContinueWhenAny {Thread.CurrentThread.ManagedThreadId.ToString("00")}")));
b.所有任務結束回調
taskList.Add(taskFactory.ContinueWhenAll(taskList.ToArray(), tList => Console.WriteLine($"這里是ContinueWhenAll {Thread.CurrentThread.ManagedThreadId.ToString("00")}")));
c.單個任務結束回調
Task task2 = taskFactory.StartNew(t => this.DoSomethingLong("btnTask_Click_005"), "煎餅果子").ContinueWith(t => Console.WriteLine($"這里是{t.AsyncState}的回調"));
Task等待
Task.WaitAny(taskList.ToArray());//卡界面 Task.WaitAll(taskList.ToArray());//卡界面
Task獲取返回結果
Task<int> intTask = taskFactory.StartNew(() => 123); int iResult = intTask.Result;
Task<string> intTask = taskFactory.StartNew(() => "123"); int iResult = intTask.Result;
Task同步執行
可以用task.RunSynchronously() 來同步執行,但是這種方式執行,只有通過new 實例化的task才有效,原因也很簡單,其他兩種方式創建task都已經自啟動執行了,不可能在來一個同步啟動執行吧。
也可以通過task.wait()來變相的實現同步執行效果,當然也可以用task.Result來變現的實現,原理很簡單,因為wait()和Result都是要阻塞主流程,直到task執行完畢
