c#异步编程一

1.什么是异步html

程序启动时,系统会在内存中建立一个新的进程,进程是构成运行程序的资源合集,c#

在进程内部,系统建立了一个称为线程的内核对象,它表明了真正执行的程序,异步

关于线程:async

默认状况下,一个进程只包含一个线程,从程序开始一直执行到结束,post

线程能够派生其余线程,所以在任意时刻,一个进程均可能包含不一样状态的多个线程,来执行程序的不一样部分,性能

系统为处理器执行所规划的单元是线程,不是进程,spa

不使用异步示例:pwa

 class MyDownload
    {
        Stopwatch sw = new Stopwatch();

        public void DoRun()
        {
            const int LargeNumber = 6000000;

            sw.Start();

            int t1 = CountCharacters(1, "http://www.miscrosoft.com");
            int t2 = CountCharacters(2, "http://www.illustratedcsharp.com");

            CountToALargeNumber(1, LargeNumber);
            CountToALargeNumber(2, LargeNumber);
            CountToALargeNumber(3, LargeNumber);
            CountToALargeNumber(4, LargeNumber);

            Console.WriteLine("Chars in http://www.miscrosoft.com  {0}", t1);
            Console.WriteLine("Chars in http://www.illustratedcsharp.com {0}", t2);
        }

        private int CountCharacters(int id, string uristring)
        {
            WebClient wc1 = new WebClient();
            Console.WriteLine("Starting call {0}  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
            string result = wc1.DownloadString(new Uri(uristring));
            Console.WriteLine("  Call {0} completed  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
            return result.Length;
        }

        public void CountToALargeNumber(int id, int value)
        {
            for (long i = 0; i < value; i++) ;
            Console.WriteLine("  End counting {0}  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
        }

    }
 class Program
    {
        static void Main(string[] args)
        {
            MyDownload md = new MyDownload();
            md.DoRun();
            Console.ReadKey();
        }
    }

若是咱们能初始化两个CountCharacter调用,无需等待结果,而是直接执行4个CountToALargeNumber调用,而后在两个CountCharacter方法调用结束后在获取结果,就能够显著的提高性能,即async/await,线程

class MyDownload
    {
        Stopwatch sw = new Stopwatch();

        public void DoRun()
        {
            const int LargeNumber = 6000000;

            sw.Start();

            Task<int> t1 = CountCharactersAsync(1, "http://www.miscrosoft.com");
            Task<int> t2 = CountCharactersAsync(2, "http://www.illustratedcsharp.com");

            CountToALargeNumber(1, LargeNumber);
            CountToALargeNumber(2, LargeNumber);
            CountToALargeNumber(3, LargeNumber);
            CountToALargeNumber(4, LargeNumber);

            Console.WriteLine("Chars in http://www.miscrosoft.com  {0}", t1.Result);
            Console.WriteLine("Chars in http://www.illustratedcsharp.com {0}", t2.Result);
        }

        private async Task<int> CountCharactersAsync(int id, string uristring)
        {
            WebClient wc1 = new WebClient();
            Console.WriteLine("Starting call {0}  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
            string result = await wc1.DownloadStringTaskAsync(new Uri(uristring));
            Console.WriteLine("  Call {0} completed  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
            return result.Length;
        }

        public void CountToALargeNumber(int id, int value)
        {
            for (long i = 0; i < value; i++) ;
            Console.WriteLine("  End counting {0}  :  {1, 4:N0} ms", id, sw.Elapsed.TotalMilliseconds);
        }

    }
 class Program
    {
        static void Main(string[] args)
        {
            MyDownload md = new MyDownload();
            md.DoRun();
            Console.ReadKey();
        }
    }

这些线程都是在主线程中完成的,咱们没有建立任何额外的线程,3d

2.asyncawait结构

若是一个程序调用某个方法,等待其执行全部处理后才继续执行,这样的方法为同步方法,

异步方法为处理完成以前就返回到调用方法,

c#的async/await特性能够建立并使用异步方法,该特性由三个部分组成,

调用方法:该方法调用异步方法,而后在异步方法执行其任务的时候继续执行,

异步方法:该方法执行异步工做,而后当即返回到调用方法

await表达式:用于异步方法内部,指明须要异步执行的任务,一个异步方法能够包含任意多个await表达式,若是一个不包含编译器会发出警告,

调用方法以下:

 class Program
    {
        static void Main(string[] args)
        {
            Task<int> value = DoAsyncStuff.CalculateSumAsync(5, 6); // 调用方法
            Console.WriteLine("value:{0}", value.Result);
            Console.ReadKey();
        }
    }

异步方法以下:

 static class DoAsyncStuff
    {
        public static async Task<int> CalculateSumAsync(int n1, int n2)
        {
            int sum = await Task.Run(() => GetSum(n1, n2)); // 异步方法 await表达式
            return sum;
        }

        private static int GetSum(int n1, int n2)
        {
            return n1 + n2;
        }
    }

3.什么是异步方法

语法上,异步方法具备以下特色:
方法头包含async方法修饰符,
包含一个或多个await表达式,
必须具有如下三种返回类型:Task<T>,Task,void,
异步方法的参数能够为任意类型的任意数量,但不能为out和ref参数,
按照约定,异步方法的名称应该以Async为后缀,
除了方法之外,lambda表达式和匿名方法也能够做为异步对象,

使用返回Task<int>对象的异步方法

class Program
    {
        static void Main(string[] args)
        {
            Task<int> value = DoAsyncStuff.CalculateSumAsync(5, 6);
            Console.WriteLine("value:{0}", value.Result);
            Console.ReadKey();
        }
    }

    static class DoAsyncStuff
    {
        public static async Task<int> CalculateSumAsync(int n1, int n2)
        {
            int sum = await Task.Run(() => GetSum(n1, n2));
            return sum;
        }

        private static int GetSum(int n1, int n2)
        {
            return n1 + n2;
        }
    }

使用返回Task对象的异步方法

 class Program
    {
        static void Main(string[] args)
        {
            Task value = DoAsyncStuff.CalculateSumAsync(5, 6);
            value.Wait();
            Console.WriteLine("Async stuff is done");
            Console.ReadKey();
        }
    }

    static class DoAsyncStuff
    {
        public static async Task CalculateSumAsync(int n1, int n2)
        {
            int sum = await Task.Run(() => GetSum(n1, n2));
            Console.WriteLine("sum:{0}", sum);
        }

        private static int GetSum(int n1, int n2)
        {
            return n1 + n2;
        }
    }

使用“调用并忘记”的异步方法

 class Program
    {
        static void Main(string[] args)
        {
            DoAsyncStuff.CalculateSumAsync(5, 6);
            Thread.Sleep(200);
            Console.WriteLine("Program Exiting");
            Console.ReadKey();
        }
    }

    static class DoAsyncStuff
    {
        public static async void CalculateSumAsync(int n1, int n2)
        {
            int sum = await Task.Run(() => GetSum(n1, n2));
            Console.WriteLine("sum:{0}", sum);
        }

        private static int GetSum(int n1, int n2)
        {
            return n1 + n2;
        }
    }

qq

转载于:https://www.cnblogs.com/huangxuQaQ/p/10861937.html