C#并行库Task类介绍

 更新时间:2022年06月16日 11:23:19   作者:天方  
这篇文章介绍了C#并行库Task类,文中通过示例代码介绍的非常详细。对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下

Task和ThreadPool的功能类似,可以用来创建一些轻量级的并行任务。对于将一个任务放进线程池

ThreadPool.QueueUserWorkItem(A);

这段代码用Task来实现的话,方式如下:

Task.Create(A);

这两端代码的使用和实现的功能都十分相似。但和TheadPool相比,Task有着更多的功能,更加方便我们使用。

Task.WaitAll()该函数的功能是等待多个任务等待任务完成,这在线程同步时经常需要用到。

假如我们要创建三个任务,并等待它们完成。这个功能用TheadPool实现如下:

    using (ManualResetEvent mre1 = new ManualResetEvent(false))
    using (ManualResetEvent mre2 = new ManualResetEvent(false))
    using (ManualResetEvent mre3 = new ManualResetEvent(false))
    {
        ThreadPool.QueueUserWorkItem(delegate
        {
            A();
            mre1.Set();
        });
        ThreadPool.QueueUserWorkItem(delegate
        {
            B();
            mre2.Set();
        });
        ThreadPool.QueueUserWorkItem(delegate
        {
            C();
            mre3.Set();
        });
        WaitHandle.WaitAll(new WaitHandle[] { mre1, mre2, mre3 });
    }

用Task类实现起来就相对简单多了:

    Task t1 = Task.Create(delegate { A(); });
    Task t2 = Task.Create(delegate { B(); });
    Task t3 = Task.Create(delegate { C(); });
    t1.Wait();
    t2.Wait();
    t3.Wait();

或者我们还可以这么写:

    Task t1 = Task.Create(delegate { A(); });
    Task t2 = Task.Create(delegate { B(); });
    Task t3 = Task.Create(delegate { C(); });
    Task.WaitAll(t1, t2, t3);
  • Task.Cancel和Task.CancelAndWait这个是一个成员函数,用于取消已经创建的Task,如果该Task正在执行中,该函数并不终止Task的执行,只是将IsCanceled属性设置为true。
    Task.Cancel和Task.CancelAndWait的区别在于:Task.CancelAndWait除了取消Task外,还将等待该Task执行完成(如果该Task在执行中)。

  • Task.ContinueWith该成员函数的作用是在执行完Task后,再执行一个后续操作。这也是一个比较有用的功能,由于比较简单,就不介绍了。

除了上述介绍的几个方法外,Task还有一些比较有用的属性和方法,也非常简单,直接参看其说明文档即可。

TaskManager和TaskManagerPolicy

这两个类主要是对Task的策略进行管理,主要管理的属性包括:最少处理Task的处理器个数、理想处理Task的处理器个数、理想的处理线程数及优先级几个属性。

在Task中使用TaskManager非常简单,只要在创建Task时将manager传入构造函数中即可。如下例所示:

    var manager = new TaskManager(new TaskManagerPolicy(1, 1,1));
    var t1 = Task.Create(x => Thread.Sleep(2000), manager);
    var t2 = Task.Create(x => Thread.Sleep(2000), manager);

    var start = DateTime.Now;
    Task.WaitAll(t1, t2);
    var end = DateTime.Now;

    Console.WriteLine(end-start);

在这里我将处理线程个数设置了为1,这样的话,只有一个线程来处理Task,执行这两个Task总共花费的时间为4秒;而在使用默认manager时候,这两个任务是并发执行的,只需要两秒即可执行完成。

异常处理

当Task在执行过程中发生异常时,该异常会在Wait或WaitAll函数中重新throw。可以通过Task的Exception属性来获取发生的异常。

    var t1 = Task.Create(x => { throw new Exception("t1 error occor"); });
    var t2 = Task.Create(x => { throw new Exception("t2 error occor"); });

    try
    {
        Task.WaitAll(t1, t2);
    }
    catch(Exception)
    {
        Console.WriteLine(t1.Exception.InnerException.Message);
        Console.WriteLine(t2.Exception.InnerException.Message);
    }

另外,顺带简单的介绍一下Future类,这个类的功能和用法和Task非常相似,完全可以看做一个带返回值的Task。示例如下:

    var f1 = Future.Create(() => 3);

    f1.Wait();
    Console.WriteLine(f1.Value);

到此这篇关于C#并行库Task类的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

相关文章

  • C#控制Excel Sheet使其自适应页宽与列宽的方法

    C#控制Excel Sheet使其自适应页宽与列宽的方法

    这篇文章主要介绍了C#控制Excel Sheet使其自适应页宽与列宽的方法,涉及C#操作Excel的相关技巧,具有一定参考借鉴价值,需要的朋友可以参考下
    2016-06-06
  • unity 鼠标移入弹出UI的操作

    unity 鼠标移入弹出UI的操作

    这篇文章主要介绍了unity 鼠标移入弹出UI的操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2021-04-04
  • C#通过属性名字符串获取、设置对象属性值操作示例

    C#通过属性名字符串获取、设置对象属性值操作示例

    这篇文章主要介绍了C#通过属性名字符串获取、设置对象属性值操作,结合实例形式总结分析了C#通过反射获取对象属性值并设置属性值,获取对象的所有属性名称及类型等相关操作技巧,需要的朋友可以参考下
    2020-03-03
  • C#字符串使用密钥进行加解密

    C#字符串使用密钥进行加解密

    这篇文章主要为大家详细介绍了C#字符串使用密钥进行加解密的代码,C#字符串加密和解密实现代码,感兴趣的小伙伴们可以参考一下
    2016-08-08
  • C#实现文件压缩与解压的方法示例【ZIP格式】

    C#实现文件压缩与解压的方法示例【ZIP格式】

    这篇文章主要介绍了C#实现文件压缩与解压的方法,结合具体实例形式分析了C#针对文件进行zip格式压缩与解压缩的相关操作技巧,需要的朋友可以参考下
    2017-06-06
  • 使用 C# 下载文件的多种方法小结

    使用 C# 下载文件的多种方法小结

    本文从最简单的下载方式开始步步递进,讲述了文件下载过程中的常见问题并给出了解决方案。并展示了如何使用多线程提升 HTTP 的下载速度以及调用 aria2 实现非 HTTP 协议的文件下载,对C# 下载文件相关知识感兴趣的朋友一起看看吧
    2021-08-08
  • C#基础之泛型

    C#基础之泛型

    泛型是 2.0 版 C# 语言和公共语言运行库 (CLR) 中的一个新功能。接下来通过本文给大家介绍c#基础之泛型,感兴趣的朋友一起学习吧
    2016-08-08
  • Unity UGUI的Dropdown下拉菜单组件使用详解

    Unity UGUI的Dropdown下拉菜单组件使用详解

    这篇文章主要为大家介绍了Unity UGUI的Dropdown下拉菜单组件使用详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-07-07
  • C#使用Fleck实现创建WebSocket服务器

    C#使用Fleck实现创建WebSocket服务器

    这篇文章主要为大家详细介绍了C#如何使用Fleck实现创建WebSocket服务器,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下
    2024-01-01
  • WPF+SkiaSharp实现自绘弹幕效果

    WPF+SkiaSharp实现自绘弹幕效果

    这篇文章主要为大家详细介绍了如何利用WPF和SkiaSharp实现自制弹幕效果,文中的示例代码讲解详细,对我们学习或工作有一定帮助,感兴趣的小伙伴可以了解一下
    2022-09-09

最新评论