Task 与 Thread 相比的优势及常见API

一、Task 与 Thread 相比的优势

  1. 更高的抽象层次

    • Task 代表一个异步操作,它是基于任务并行库(Task Parallel Library,TPL)构建的,提供了更高层次的抽象,让开发者无需直接处理底层的线程创建和管理。相比之下,Thread 是一个较低层次的构造,直接操作线程需要更多的代码和对线程状态的管理。
    • 例如,使用 Task 可以轻松地表示一个异步的文件下载操作,而无需关心线程的具体创建和调度细节。
  2. 更好的资源管理

    • Task 由任务调度器自动管理,可以根据系统资源和负载情况进行优化调度。而手动创建大量的 Thread 可能会导致资源过度消耗和性能问题,尤其是在创建大量线程时可能会耗尽系统资源。
    • Task 可以自动复用线程,减少线程创建和销毁的开销,提高系统的资源利用率。
  3. 易于组合和等待

    • Task 可以方便地进行组合和等待。可以使用 Task.WhenAll 和 Task.WhenAny 等方法来等待多个任务完成,或者将多个任务组合成一个更复杂的任务。这使得异步编程更加灵活和易于管理。
    • 例如,当需要同时下载多个文件并在所有文件下载完成后进行处理时,可以使用 Task.WhenAll 轻松实现。
  4. 支持异步编程模式

    • Task 与 C# 的异步编程模式(async/await)紧密结合,使得异步编程更加简洁和易于理解。使用 async/await 可以像编写同步代码一样编写异步代码,提高代码的可读性和可维护性。
    • 相比之下,使用 Thread 进行异步编程需要手动处理线程的同步和等待,代码更加复杂和难以维护。
  5. 异常处理更方便

    • Task 提供了统一的方式来处理异步操作中的异常。当一个 Task 抛出异常时,可以在调用代码中使用 try/catch 块来捕获异常,而无需像处理 Thread 那样手动检查线程的异常状态。
    • 例如,如果一个异步任务在执行过程中发生异常,可以在等待任务完成的代码中捕获并处理这个异常。

二、Task 的常用 API

  1. Task.Run(Action action)

    • 用于在后台线程上执行一个指定的操作。它接受一个无参数无返回值的委托(Action)作为参数,并返回一个表示该操作的 Task 对象。
    • 例如:Task.Run(() => Console.WriteLine("Running in a background task."));
  2. Task.Factory.StartNew(Action action)

    • 与 Task.Run 类似,也用于在后台线程上启动一个新任务。它提供了更多的配置选项,可以指定任务的创建选项、调度器等。
    • 例如:Task.Factory.StartNew(() => Console.WriteLine("Started with more options."), TaskCreationOptions.LongRunning);
  3. Task.WhenAll(Task[] tasks)

    • 等待一组任务全部完成。它接受一个 Task 对象数组作为参数,并返回一个新的 Task 对象,当所有输入任务都完成时,这个新任务也完成。
    • 例如:var task1 = Task.Run(() => { Thread.Sleep(1000); return 1; });
      var task2 = Task.Run(() => { Thread.Sleep(2000); return 2; });
      await Task.WhenAll(task1, task2);
  4. Task.WhenAny(Task[] tasks)

    • 等待一组任务中的任何一个完成。它接受一个 Task 对象数组作为参数,并返回一个新的 Task 对象,当任何一个输入任务完成时,这个新任务也完成,并返回完成的那个任务。
    • 例如:var task1 = Task.Run(() => { Thread.Sleep(1000); return 1; });
      var task2 = Task.Run(() => { Thread.Sleep(2000); return 2; });
      var completedTask = await Task.WhenAny(task1, task2);
  5. Task.Wait()

    • 阻塞当前线程,直到任务完成。如果任务出现异常,会抛出 AggregateException,其中包含任务中的所有异常。
    • 例如:var task = Task.Run(() => { Thread.Sleep(1000); throw new Exception("Task failed."); });
      try { task.Wait(); } catch (AggregateException ex) { Console.WriteLine(ex.InnerException.Message); }
  6. Task.Result

    • 获取任务的结果。如果任务还未完成,调用此属性会阻塞当前线程,直到任务完成并返回结果。如果任务出现异常,会抛出包含异常信息的 AggregateException
    • 例如:var task = Task.Run(() => { return 42; });
      int result = task.Result;
      Console.WriteLine(result);
  7. Task.Delay(int millisecondsDelay)

    • 创建一个异步任务,在指定的时间延迟后完成。这个方法通常用于模拟异步等待或实现定时操作。
    • 例如:await Task.Delay(2000);
      Console.WriteLine("Delayed for 2 seconds.");

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/889651.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

爬虫prc技术----小红书爬取解决xs

知识星球:知识星球 | 深度连接铁杆粉丝,运营高品质社群,知识变现的工具知识星球是创作者连接铁杆粉丝,实现知识变现的工具。任何从事创作或艺术的人,例如艺术家、工匠、教师、学术研究、科普等,只要能获得一…

【redis-06】redis的stream流实现消息中间件

redis系列整体栏目 内容链接地址【一】redis基本数据类型和使用场景https://zhenghuisheng.blog.csdn.net/article/details/142406325【二】redis的持久化机制和原理https://zhenghuisheng.blog.csdn.net/article/details/142441756【三】redis缓存穿透、缓存击穿、缓存雪崩htt…

STM32-ADC模数转换

一、概述 ADC(Analog-Digital Converter)模拟-数字转换器 ADC可以将引脚上连续变化的模拟电压转换为内存中存储的数字变量,建立模拟电路到数字电路的桥梁12位逐次逼近型ADC,1us转换时间输入电压范围:0~3.3V&#xff…

vscode配置R语言debugger环境:“vscDebugger“的安装

要在 R 中安装 vscDebugger 包,可以按照以下步骤进行: 方法一:使用命令面板自动安装 打开命令面板: 在 Visual Studio Code 中按 CtrlShiftP 打开命令面板。 运行安装命令: 在命令面板中输入并选择 r.debugger.updat…

大数据新视界 --大数据大厂之 Dremio:改变大数据查询方式的创新引擎

💖💖💖亲爱的朋友们,热烈欢迎你们来到 青云交的博客!能与你们在此邂逅,我满心欢喜,深感无比荣幸。在这个瞬息万变的时代,我们每个人都在苦苦追寻一处能让心灵安然栖息的港湾。而 我的…

前端的全栈混合之路Meteor篇:分布式数据协议DDP深度剖析

本文属于进阶篇,并不是太适合新人阅读,但纯粹的学习还是可以的,因为后续会实现很多个ddp的版本用于web端、nodejs端、安卓端和ios端,提前预习和复习下。ddp协议是一个C/S架构的协议,但是客户端也同时可以是服务端。 什…

SSD |(二)SSD主控

文章目录 📚控制器架构🐇PCIe和NVMe控制器前端子系统🐇NAND闪存控制器后端子系统🐇内存子系统🐇安全子系统🐇CPU计算子系统 📚控制器架构 控制器作为一个片上系统,处理来自用户端的…

【二分算法】——8个题目让你找到二分算法的感觉势如破竹

文章目录 1.二分查找2.在排序数组中查找元素的第一个和最后一个位置3.x的平方根4.搜索插入位置5.山脉数组的峰顶索引6.寻找峰值7.寻找旋转排序数组中的最小值8.JZ53(2) 1.二分查找 https://leetcode.cn/problems/binary-search/ 思路: 标准的二分查找。给定一个有序数组和目…

【2024版本】Mac/Windows IDEA安装教程

IDEA 2024版本真的很强大,此外JDK发布了最新稳定版 JDK21 ,只有新版本支持JDK 21、JDK22。原来数据库插件不支持redis等一些NoSql的数据库的连接,如果要使用需要自己单独装收费的插件。直接打开idea就很吃内存了,再打开其他一大堆…

47 C 语言实战项目——家庭收支记账软件

目录 1 需求说明 1.1 菜单显示 1.2 登记收入 1.3 登记支出 1.4 显示收支明细 1.5 退出 2 流程分析 2.1 总流程图 2.2 登记收入流程图 2.3 登记支出流程图 2.4 收支明细流程图 2.5 退出流程图 3 代码实现 3.1 框架搭建 3.2 收支明细功能 3.3 登记收入功能 3.4 …

23年408数据结构

第一题: 解析: 第一点,我们要知道顺序存储的特点:优点就是随用随取,就是你想要查询第几个元素可以直接查询出来,时间复杂度就是O(1),缺点就是不适合删除和插入,因为每次删除和插入一…

【数据分享】2000—2023年我国省市县三级逐年植被覆盖度(FVC)数据(Shp/Excel格式)

之前我们分享过2000—2023年逐月植被覆盖度(FVC)栅格数据(可查看之前的文章获悉详情)和Excel和Shp格式的省市县三级逐月FVC数据(可查看之前的文章获悉详情),原始的逐月栅格数据来源于高吉喜学者…

青云AI算力创新:直击AI落地痛点 打造企业数智化基石

在当今这个数字化、智能化的时代,企业数字化转型、智能化升级应用实践在加速,AI算力已经成为企业数字化转型和智能化升级的重要基石,而AI算力在推动技术创新和业务增长中起到了关键作用。青云科技近日举办的AI算力发布会,标志着AI…

知识图谱入门——5:Neo4j Desktop安装和使用手册(小白向:Cypher 查询语言:逐步教程!Neo4j 优缺点分析)

Neo4j简介 Neo4j 是一个基于图结构的 NoSQL 数据库,专门用于存储、查询和管理图形数据。它的核心思想是使用节点、关系和属性来描述数据。图数据库非常适合那些需要处理复杂关系的数据集,如社交网络、推荐系统、知识图谱等领域。 与传统的关系型数据库…

如何快速给word文件加拼音?请跟着步骤完成吧

如何快速给word文件加拼音?在日常工作中,我们时常会遇到需要为Word文件中的文字添加拼音的情况,这尤其在教育、出版或国际交流等领域显得尤为重要。为文字配上拼音,不仅能帮助学习者准确发音,还能提升文档的可读性和普…

【JavaEE初阶】深入理解不同锁的意义,synchronized的加锁过程理解以及CAS的原子性实现(面试经典题);

前言 🌟🌟本期讲解关于锁的相关知识了解,这里涉及到高频面试题哦~~~ 🌈上期博客在这里:【JavaEE初阶】深入理解线程池的概念以及Java标准库提供的方法参数分析-CSDN博客 🌈感兴趣的小伙伴看一看小编主页&am…

【STM32单片机_(HAL库)】4-2-1【定时器TIM】定时器输出PWM实现呼吸灯实验

1.硬件 STM32单片机最小系统LED灯模块 2.软件 pwm驱动文件添加定时器HAL驱动层文件添加GPIO常用函数定时器输出PWM配置步骤main.c程序 #include "sys.h" #include "delay.h" #include "led.h" #include "pwm.h"int main(void) {HA…

【瑞萨RA8D1 CPK开发板】串口的使用和STDOUT输出重定向

串口 本次串口的使用关于时钟导致串口的波特率不对,坑了我很久的时间 使能时钟 串口发现一个问题就是,只能使用下边的时钟配置,修改时钟源和分频系数都会导致串口波特率不正常,这种问题出现在mdkrasc的使用场景之下&#xff1b…

adaptor lora基础

https://www.zhihu.com/question/508658141/answer/3340979311 adaptor和PEFT的区别:前者在模型子层后加一个小型的dense;后者直接稀疏化模型本身; Loading Pre-Trained Adapters — AdapterHub documentation CVPR 2024 | SD-DiT&#xff…

Python | Leetcode Python题解之第468题验证IP地址

题目: 题解: class Solution:def validIPAddress(self, queryIP: str) -> str:if queryIP.find(".") ! -1:# IPv4last -1for i in range(4):cur (len(queryIP) if i 3 else queryIP.find(".", last 1))if cur -1:return &q…