创建Task的3种方法
-
new方式实例化一个Task
//task.Start方式,每个task都在不同的线程中 ,不会阻塞主线程 Task task = new Task(DoActionTask); task.Start(); //方式,每个任务都在同一个线程。task会阻塞主线程 task.RunSynchronously();
-
Task.Factory.StartNew(Action action)创建和启动一个Task
//创建和启动一个Task Task.Factory.StartNew(DoActionTask);
-
Task.Run(Action action)将任务放在线程池队列,返回并启动一个Task
//将任务放在线程池队列,返回并启动一个Task Task.Run(DoActionTask);
Task的Wait/WaitAny/WaitAll方法
- task.Wait()
表示等待task执行完毕
- Task.WaitAll(Task[] tasks)
阻塞当前线程,直到全部task都执行完成-再解除阻塞 ---主线程被阻塞,所以卡界面
- Task.WaitAny(Task[] tasks)
阻塞当前线程,任意task执行完毕就解除阻塞 ---主线程被阻塞,所以卡界面
Task的延续操作(WhenAny/WhenAll/ContinueWith)
- ContinueWhenAll
等着全部任务完成后,启动一个新的task来完成后续动作 --不卡界面 - ContinueWhenAny
等着任一任务完成后,启动一个新的task来完成后续动作 - WhenAll
等着全部任务完成后, 创建一个任务,
List<Task> tasks = new List<Task>();
tasks.Add(Task.Run(() => ReadFile()));
tasks.Add(Task.Run(() => LoadApi("url")));
tasks.Add(Task.Run(() => LoadDB()));
//阻塞当前线程,直到全部task都执行完成-再解除阻塞 ---主线程被阻塞,所以卡界面
Task.WaitAll(tasks.ToArray());
//阻塞当前线程,任意task执行完毕就解除阻塞 ---主线程被阻塞,所以卡界面
Task.WaitAny(tasks.ToArray());
TaskFactory taskFactory = new TaskFactory();
//等着全部任务完成后,启动一个新的task来完成后续动作 --不卡界面
taskFactory.ContinueWhenAll(tasks.ToArray(), t =>
{
Console.WriteLine($"{Thread.CurrentThread.ManagedThreadId} ---Tasks全部执行完毕---{DateTime.Now}");
});
//等着任一任务完成后,启动一个新的task来完成后续动作
taskFactory.ContinueWhenAny(tasks.ToArray(), t =>
{
Console.WriteLine($"{Thread.CurrentThread.ManagedThreadId} ---其中一个执行完毕---{DateTime.Now}");
});
//等着全部任务完成后, 创建一个任务,
Task.WhenAll(Task.Run(ReadFile), Task.Run(() => LoadApi("url")), Task.Run(LoadDB)).ContinueWith((t) =>
{
Console.WriteLine("Tasks全部执行完毕");
});