C#线程学习笔记八:async & await入门一
一、涉及内容
async & await是C# 5.0引入的,控制台输出所使用的$符号(拼接字符串)是C# 6.0引入的,其功能类似于string.Format()方法。
二、多线程、异步、同步之间的联系与区别
厨房案例:
比如说你要炒5道菜ABCDE,但是只有两个炉子可以用,即同时只能炒两道菜。在这里,炉子就是线程。
假如两个炉子分别同时炒A和B,那剩下的CDE只能等A或B炒完了才能开始。这个等待的过程就是同步,我们称之为阻塞,即这个时候你只能炒A和B这两道菜。
假如你还有一台咖啡机,在你炒A和B的时候顺手把咖啡豆和水放到咖啡机里打开开关,然后你就不用管它了。此时,就是新开了一个线程去煮咖啡,而煮咖啡
是由咖啡机自动完成的并不影响继续炒菜,所以煮咖啡这个线程是异步的,我们称之为非阻塞。
当咖啡机叮的一声通知你咖啡已经煮好了,你要去把咖啡拿出来加点糖或奶什么的,这个拿咖啡的动作我们称之为回调,这个是咖啡机线程完成之后通知你要去
做的动作。
简单来说:
会占用你的时间让你无法去做其它事情的任务叫做同步任务(炒菜要专注否则会糊锅)。
那些不需要占用你的时间的任务叫做异步任务(咖啡机自己会把咖啡煮好,不需要你一直看着它)。
下面代码演示不使用异步的情况:
class Program
{
//创建计时器
private static readonly Stopwatch stopwatch = new Stopwatch(); static void Main(string[] args)
{
#region async & await入门一之不使用异步
//启动计时器
stopwatch.Start();
//URL地址
const string url1 = "http://www.cnblogs.com/";
const string url2 = "http://www.cnblogs.com/atomy/";
//异步下载某网站内容,并统计字符的个数。
var result1 = CountCharacters("url1", url1);
var result2 = CountCharacters("url2", url2);
//主要是通过拼接字符串达到耗时操作
for (var i = ; i < ; i++)
{
ExtraOperation(i + );
}
//控制台输出
Console.WriteLine($"{url1} 的字符个数:{result1}");
Console.WriteLine($"{url2} 的字符个数:{result2}");
Console.WriteLine($"总耗时{stopwatch.ElapsedMilliseconds}ms。");
Console.Read();
#endregion
} /// <summary>
/// 统计字符个数
/// </summary>
/// <param name="id"></param>
/// <param name="address"></param>
/// <returns></returns>
private static int CountCharacters(string name, string address)
{
var wc = new WebClient();
Console.WriteLine($"{name}开始调用,历时{stopwatch.ElapsedMilliseconds}ms,线程id={Thread.CurrentThread.ManagedThreadId}。"); var result = wc.DownloadString(address);
Console.WriteLine($"{name}调用完成,历时{stopwatch.ElapsedMilliseconds}ms,线程id={Thread.CurrentThread.ManagedThreadId}。"); return result.Length;
} /// <summary>
/// 额外操作
/// </summary>
/// <param name="id"></param>
private static void ExtraOperation(int id)
{
//这里是通过拼接字符串进行一些相对耗时的操作
var s = "";
for (var i = ; i < ; i++)
{
s += i;
}
Console.WriteLine($"第{id}次ExtraOperation执行完成,历时:{stopwatch.ElapsedMilliseconds}ms。");
}
}
运行结果如下:

下面代码演示使用异步的情况:
class Program
{
//创建计时器
private static readonly Stopwatch stopwatch = new Stopwatch(); static void Main(string[] args)
{
#region async & await入门一之使用异步
//启动计时器
stopwatch.Start();
//URL地址
const string url1 = "http://www.cnblogs.com/";
const string url2 = "http://www.cnblogs.com/atomy/";
//异步下载某网站内容,并统计字符的个数。
Task<int> t1 = CountCharactersAsync("url1", url1);
Task<int> t2 = CountCharactersAsync("url2", url2);
//主要是通过拼接字符串达到耗时操作
for (var i = ; i < ; i++)
{
ExtraOperation(i + );
}
//控制台输出
Console.WriteLine($"{url1} 的字符个数:{t1.Result}");
Console.WriteLine($"{url2} 的字符个数:{t2.Result}");
Console.WriteLine($"总耗时{stopwatch.ElapsedMilliseconds}ms。");
Console.Read();
#endregion
} /// <summary>
/// 统计字符个数
/// </summary>
/// <param name="id"></param>
/// <param name="address"></param>
/// <returns></returns>
private static async Task<int> CountCharactersAsync(string name, string address)
{
var wc = new WebClient();
Console.WriteLine($"{name}开始调用,历时{stopwatch.ElapsedMilliseconds}ms,线程id={Thread.CurrentThread.ManagedThreadId}。"); var result =await wc.DownloadStringTaskAsync(address);
Console.WriteLine($"{name}调用完成,历时{stopwatch.ElapsedMilliseconds}ms,线程id={Thread.CurrentThread.ManagedThreadId}。"); return result.Length;
} /// <summary>
/// 额外操作
/// </summary>
/// <param name="id"></param>
private static void ExtraOperation(int id)
{
//这里是通过拼接字符串进行一些相对耗时的操作
var s = "";
for (var i = ; i < ; i++)
{
s += i;
}
Console.WriteLine($"第{id}次ExtraOperation执行完成,历时:{stopwatch.ElapsedMilliseconds}ms。");
}
}
运行结果如下:

三、async & await 结构
async & await结构可分成三部分:
1)调用方法:该方法调用异步方法,然后在异步方法执行其任务的时候继续执行。
2)异步方法:该方法异步执行工作,然后立刻返回到调用方法。
3)await表达式:用于异步方法内部,指出需要异步执行的任务。


四、异步方法
异步方法:在执行完成前立即返回调用方法,在调用方法继续执行的过程中完成任务。
语法分析:

参考自:
https://www.cnblogs.com/woxihuadabai/p/8042652.html
https://www.cnblogs.com/liqingwen/p/5831951.html
C#线程学习笔记八:async & await入门一的更多相关文章
- Java IO学习笔记八:Netty入门
作者:Grey 原文地址:Java IO学习笔记八:Netty入门 多路复用多线程方式还是有点麻烦,Netty帮我们做了封装,大大简化了编码的复杂度,接下来熟悉一下netty的基本使用. Netty+ ...
- C#线程学习笔记九:async & await入门二
一.异步方法返回类型 只能返回3种类型(void.Task和Task<T>). 1.1.void返回类型:调用方法执行异步方法,但又不需要做进一步的交互. class Program { ...
- C#线程学习笔记十:async & await入门三
一.Task.Yield Task.Yield简单来说就是创建时就已经完成的Task,或者说执行时间为0的Task,或者说是空任务,也就是在创建时就将Task的IsCompeted值设置为0. 我们知 ...
- Oracle RAC学习笔记:基本概念及入门
Oracle RAC学习笔记:基本概念及入门 2010年04月19日 10:39 来源:书童的博客 作者:书童 编辑:晓熊 [技术开发 技术文章] oracle 10g real applica ...
- Linux内核学习笔记-1.简介和入门
原创文章,转载请注明:Linux内核学习笔记-1.简介和入门 By Lucio.Yang 部分内容来自:Linux Kernel Development(Third Edition),Robert L ...
- js学习笔记:webpack基础入门(一)
之前听说过webpack,今天想正式的接触一下,先跟着webpack的官方用户指南走: 在这里有: 如何安装webpack 如何使用webpack 如何使用loader 如何使用webpack的开发者 ...
- jQuery学习笔记 - 基础知识扫盲入门篇
jQuery学习笔记 - 基础知识扫盲入门篇 2013-06-16 18:42 by 全新时代, 11 阅读, 0 评论, 收藏, 编辑 1.为什么要使用jQuery? 提供了强大的功能函数解决浏览器 ...
- Learning ROS forRobotics Programming Second Edition学习笔记(八)indigo rviz gazebo
中文译著已经出版,详情请参考:http://blog.csdn.net/ZhangRelay/article/category/6506865 Learning ROS forRobotics Pro ...
- 【转载】【时序约束学习笔记1】Vivado入门与提高--第12讲 时序分析中的基本概念和术语
时序分析中的基本概念和术语 Basic concept and Terminology of Timing Analysis 原文标题及网址: [时序约束学习笔记1]Vivado入门与提高--第12讲 ...
随机推荐
- js 根据指定的多个索引,删除相应的数组元素。splice + sort
更新于2018-04-19 var productItems = ["a", "b", "c", "d"]; var i ...
- Shell - 长 ping 脚本监控网络时延
生产环境中, 网络时延是一个很重要的指标. 为了方便检查网络时延的大小, 我们可以通过ping命令实现长时间的网络监控. 1 ping 命令的使用 1.1 常用参数 -i: 每次执行ping操作的间隔 ...
- 开源WPF控件库MaterialDesignInXAML推荐
今天介绍一个开源的C# WPF开源控件库,非常漂亮,重点是开源哦 WPF做桌面开发是很有优势的,除了微软自带的控件外,还有很多第三方的控件库,比如收费的Dev Express For WPF.Tele ...
- 计蒜客 The Preliminary Contest for ICPC Asia Nanjing 2019
F Greedy Sequence You're given a permutation aa of length nn (1 \le n \le 10^51≤n≤105). For each ...
- linux中Nginx安装
linux中Nginx安装 编译安装 Nginx的优点太多,这里不再赘述,详情请看这篇博客深入理解nginx. Nginx的安装有rpm包安装.编译安装和docker安装.本文将介绍编译安装方 ...
- 机器学习回顾篇(11):支持向量机(SVM)
.caret, .dropup > .btn > .caret { border-top-color: #000 !important; } .label { border: 1px so ...
- kubeadm 报错 error execution phase preflight: couldn’t validate the identity of the API Server: abort connecting to API servers after timeout of 5m0s
原因:master节点的token过期了 解决:重新生成新token 在master重新生成token # kubeadm token create 424mp7.nkxx07p940mkl2nd # ...
- 洛谷P2085——最小函数值
题目描述 有n个函数,分别为\(F_1,F_2,...,F_n\).定义\(F_i(x)=A_i*x^2+B_i*x+C_i (x∈N*)\).给定这些\(A_i.B_i和C_i\),请求出所有函数的 ...
- 题解 CF1206B 【Make Product Equal One】
感谢 @一个低调的人 (UID=48417) 题目: CodeForces链接 Luogu链接 思路: 这是一个一眼题 我们不妨把所有的数都看做是\(1\)(取相应的花费,如:\(6\) 的花费就是\ ...
- hashtable基础