淄博临淄网站建设,中文wordpress企业,找网站做q币,wordpress 2015异步操作通常用于执行完成时间可能较长的任务#xff0c;如打开大文件、连接远程计算机或查询数据库。异步操作在主应用程序线程以外的线程中执行。应用程序调用方法异步执行某个操作时#xff0c;应用程序可在异步方法执行其任务时继续执行。.NET框架能够对任何方法进行异步…异步操作通常用于执行完成时间可能较长的任务如打开大文件、连接远程计算机或查询数据库。异步操作在主应用程序线程以外的线程中执行。应用程序调用方法异步执行某个操作时应用程序可在异步方法执行其任务时继续执行。 .NET框架能够对任何方法进行异步调用。进行异步调用时需要定义与异步调用的方法具有相同签名的委托。公共语言运行时会自动使用适当的签名为该委托定义BeginInvoke和EndInvoke方法。 BeginInvoke方法用于启动异步调用。它与需要异步执行的方法具有相同的参数。此外它还有两个可选参数。第一个参数是一个AsyncCallback委托该委托引用在异步调用完成时要调用的方法。第二个参数是一个用户定义的对象该对象可向回调方法传递数据。BeginInvoke立即返回不会等待异步调用完成被调用的方法将在线程池线程中执行。因此提交请求的原始线程与执行异步方法的线程池线程是并行执行的。BeginInvoke会返回一个IAsyncResult对象可以使用该对象来监视异步调用进度也可将该对象传递给EndInvoke方法以获取异步执行的方法的返回值。 EndInvoke方法用于检索异步调用的结果。调用BeginInvoke方法后可随时调用EndInvoke方法如果异步调用尚未完成EndInvoke方法将一直阻塞调用线程直到异步调用完成后才允许调用线程执行。EndInvoke方法的参数包括需要异步执行的方法的out和ref参数以及由BeginInvoke返回的IAsyncResult对象。因此通过EndInvoke方法可以获得异步调用的方法的所有输出数据包括返回值、out和ref参数。 AsyncCallback委托表示在异步操作完成时调用的回调方法其定义如下 public delegate void AsyncCallback(IAsyncResult ar); System.IAsyncResult接口表示异步操作的状态。IAsyncResult接口由包含可异步操作的方法的类实现。它是启动异步操作的方法的返回类型也是结束异步操作的方法的第三个参数的类型。当异步操作完成时IAsyncResult对象也将传递给由AsyncCallback委托调用的方法。支持IAsyncResult接口的对象存储异步操作的状态信息并提供同步对象以允许线程在操作完成时终止。IAsyncResult接口定义了四个公开属性通过它们可以获取异步调用的状态。 — AsyncState获取用户定义的对象它限定或包含关于异步操作的信息。 — AsyncWaitHandle获取用于等待异步操作完成的 WaitHandle。 — CompletedSynchronously获取异步操作是否同步完成的指示。 — IsCompleted获取异步操作是否已完成的指示。 使用BeginInvoke和EndInvoke进行异步调用的常用方法主要有四种 — 调用BeginInvoke方法启动异步方法进行某些操作然后调用EndInvoke方法来一直阻止请求线程到调用完成。 — 调用BeginInvoke方法启动异步方法使用System.IAsyncResult.AsyncWaitHandle属性获取WaitHandle使用它的WaitOne方法一直阻止执行直到发出WaitHandle信号然后调用EndInvoke方法。 — 调用BeginInvoke方法启动异步方法轮询由BeginInvoke返回的IAsyncResult确定异步调用何时完成然后调用EndInvoke。 — 调用BeginInvoke方法启动异步方法时将代表异步方法完成时需要回调的方法的委托传递给BeginInvoke。异步调用完成后将在ThreadPool线程上执行该回调方法。在该回调方法中调用EndInvoke。 每种方法都是通过BeginInvoke方法来启动异步方法调用EndInvoke方法来完成异步调用。 1直接调用EndInvoke 方法等待异步调用结束 异步执行方法的最简单的方式是通过调用委托的BeginInvoke方法来开始执行方法在主线程上执行一些工作然后调用委托的EndInvoke方法。EndInvoke可能会阻止调用线程因为它直到异步调用完成之后才返回。这种技术非常适合于文件或网络操作但是由于EndInvoke会阻止它所以不要从服务于用户界面的线程中调用它。 下面的代码说明了如何使用这种方法来进行异步调用并获得异步方法的结果 // AsynCall1.cs // 异步调用示例: 直接调用EndInvoke 方法等待异步调用结束 using System; using System.Threading; // 定义异步调用方法的委托 // 它的签名必须与要异步调用的方法一致 public delegate int AsynComputeCaller(ulong l, out ulong factorial); public class Factorial { // 计算阶乘 public ulong Compute(ulong l) { // 不要太快 :-) Thread.Sleep(50); if (l 1) { return 1; } else { return l * Compute(l - 1); } } // 要异步调用的方法 // 1. 调用Factorial方法来计算阶乘并用out参数返回 // 2. 统计计算阶乘所用的时间并返回该值 public int AsynCompute(ulong l, out ulong factorial) { Console.WriteLine(开始异步方法); DateTime startTime DateTime.Now; factorial Compute(l); TimeSpan usedTime new TimeSpan(DateTime.Now.Ticks - startTime.Ticks); Console.WriteLine(结束异步方法); return usedTime.Milliseconds; } } public class Test { public static void Main() { // 创建包含异步方法的类的实例 Factorial fact new Factorial(); // 创建异步委托 AsynComputeCaller caller new AsynComputeCaller(fact.AsynCompute); Console.WriteLine(启动异步调用); ulong l 30; ulong lf; // 启动异步调用 IAsyncResult result caller.BeginInvoke(l, out lf, null, null); // 主线程进行一些操作 Thread.Sleep(0); Console.WriteLine(主线程进行一些操作); // 调用EndInvoke来等待异步调用结束并获得结果 int returnValue caller.EndInvoke(out lf, result); // 异步调用的方法已经结束显示结果 Console.WriteLine(已经得到结果{0}的阶乘为{1}计算时间为{2}毫秒, l, lf, returnValue); } } 2使用 WaitHandle 等待异步调用结束 可以使用BeginInvoke方法返回的IAsyncResult的AsyncWaitHandle属性来获取WaitHandle。异步调用完成时会发出WaitHandle信号可以通过调用WaitOne方法来等待它。 如果使用WaitHandle则在异步调用完成之前或之后在通过调用EndInvoke检索结果之前还可以执行其他处理。 下面的代码说明了如何使用这种方法来进行异步调用并获得异步方法的结果 // AsynCall2.cs // 异步调用示例使用 WaitHandle 等待异步调用结束 using System; using System.Threading; // 定义异步调用方法的委托 // 它的签名必须与要异步调用的方法一致 public delegate int AsynComputeCaller(ulong l, out ulong factorial); public class Factorial { // 计算阶乘 public ulong Compute(ulong l) { // 不要太快 :-) Thread.Sleep(50); if (l 1) { return 1; } else { return l * Compute(l - 1); } } // 要异步调用的方法 // 1. 调用Factorial方法来计算阶乘并用out参数返回 // 2. 统计计算阶乘所用的时间并返回该值 public int AsynCompute(ulong l, out ulong factorial) { Console.WriteLine(开始异步方法); DateTime startTime DateTime.Now; factorial Compute(l); TimeSpan usedTime new TimeSpan(DateTime.Now.Ticks - startTime.Ticks); Console.WriteLine(结束异步方法); return usedTime.Milliseconds; } } public class Test { public static void Main() { // 创建包含异步方法的类的实例 Factorial fact new Factorial(); // 创建异步委托 AsynComputeCaller caller new AsynComputeCaller(fact.AsynCompute); Console.WriteLine(启动异步调用); ulong l 30; ulong lf; // 启动异步调用 IAsyncResult result caller.BeginInvoke(l, out lf, null, null); // 主线程进行一些操作 Thread.Sleep(0); Console.WriteLine(主线程进行一些操作); // 等待WaitHandle接收到信号 Console.WriteLine(等待WaitHandle接收到信号); result.AsyncWaitHandle.WaitOne(); // 主线程进行一些操作 Thread.Sleep(0); Console.WriteLine(异步方法已经结束主线程进行另外一些操作); // 调用EndInvoke来获得结果 int returnValue caller.EndInvoke(out lf, result); // 异步调用的方法已经结束显示结果 Console.WriteLine({0}的阶乘为{1}计算时间为{2}毫秒, l, lf, returnValue); } } 3轮询异步调用是否完成 可以使用由BeginInvoke方法返回的IAsyncResult的IsCompleted属性来发现异步调用何时完成。从用户界面的服务线程中进行异步调用时可以执行此操作。轮询完成允许调用线程在异步调用在线程池线程上执行时继续执行。 下面的代码说明了如何使用这种方法来进行异步调用并获得异步方法的结果 // AsynCall3.cs // 异步调用示例: 轮询异步调用是否完成 using System; using System.Threading; // 定义异步调用方法的委托 // 它的签名必须与要异步调用的方法一致 public delegate int AsynComputeCaller(ulong l, out ulong factorial); public class Factorial { // 计算阶乘 public ulong Compute(ulong l) { // 不要太快 :-) Thread.Sleep(50); if (l 1) { return 1; } else { return l * Compute(l - 1); } } // 要异步调用的方法 // 1. 调用Factorial方法来计算阶乘并用out参数返回 // 2. 统计计算阶乘所用的时间并返回该值 public int AsynCompute(ulong l, out ulong factorial) { Console.WriteLine(开始异步方法); DateTime startTime DateTime.Now; factorial Compute(l); TimeSpan usedTime new TimeSpan(DateTime.Now.Ticks - startTime.Ticks); Console.WriteLine(\n结束异步方法); return usedTime.Milliseconds; } } public class Test { public static void Main() { // 创建包含异步方法的类的实例 Factorial fact new Factorial(); // 创建异步委托 AsynComputeCaller caller new AsynComputeCaller(fact.AsynCompute); Console.WriteLine(启动异步调用); ulong l 30; ulong lf; // 启动异步调用 IAsyncResult result caller.BeginInvoke(l, out lf, null, null); // 轮询异步方法是否结束 Console.WriteLine(主线程进行一些操作); while (result.IsCompleted false) { // 主线程进行一些操作 Thread.Sleep(10); Console.Write(.); } // 主线程进行一些操作 Thread.Sleep(0); Console.WriteLine(异步方法已经结束主线程进行另外一些操作); // 调用EndInvoke来获得结果 int returnValue caller.EndInvoke(out lf, result); // 异步调用的方法已经结束显示结果 Console.WriteLine(已经得到结果{0}的阶乘为{1}计算时间为{2}毫秒, l, lf, returnValue); } } 4在异步调用完成时执行回调方法 如果启动异步调用的线程是不需要处理结果的线程则可以在调用完成时执行回调方法。回调方法在线程池线程上执行。 若要使用回调方法必须将引用回调方法的AsyncCallback委托传递给BeginInvoke。也可以传递包含回调方法将要使用的信息的对象。例如可以传递启动调用时曾使用的委托以便回调方法能够调用EndInvoke方法。 下面的代码说明了如何使用这种方法来进行异步调用并获得异步方法的结果 // AsynCall4.cs // 异步调用示例: 在异步调用完成时执行回调方法 using System; using System.Threading; // 定义异步调用方法的委托 // 它的签名必须与要异步调用的方法一致 public delegate int AsynComputeCaller(ulong l, out ulong factorial); public class Factorial { // 计算阶乘 public ulong Compute(ulong l) { // 不要太快 :-) Thread.Sleep(50); if (l 1) { return 1; } else { return l * Compute(l - 1); } } // 要异步调用的方法 // 1. 调用Factorial方法来计算阶乘并用out参数返回 // 2. 统计计算阶乘所用的时间并返回该值 public int AsynCompute(ulong l, out ulong factorial) { Console.WriteLine(开始异步方法); DateTime startTime DateTime.Now; factorial Compute(l); TimeSpan usedTime new TimeSpan(DateTime.Now.Ticks - startTime.Ticks); Console.WriteLine(结束异步方法); return usedTime.Milliseconds; } } public class Test { static ulong l 30; static ulong lf; public static void Main() { // 创建包含异步方法的类的实例 Factorial fact new Factorial(); // 创建异步委托 AsynComputeCaller caller new AsynComputeCaller(fact.AsynCompute); // 启动异步调用 Console.WriteLine(启动异步调用); IAsyncResult result caller.BeginInvoke(l, out lf, new AsyncCallback(CallbackMethod), caller); // 主线程进行一些操作 Thread.Sleep(0); Console.WriteLine(主线程进行一些操作); Console.WriteLine(按Enter键结束程序...); Console.ReadLine(); } // 在异步调用完成时执行的回调方法 // 该回调方法的签名必须与AsyncCallback委托一致 static void CallbackMethod(IAsyncResult ar) { // 获取委托 AsynComputeCaller caller (AsynComputeCaller)ar.AsyncState; // 调用EndInvoke来获得结果 int returnValue caller.EndInvoke(out lf, ar); // 异步调用的方法已经结束显示结果 Console.WriteLine(已经得到结果{0}的阶乘为{1}计算时间为{2}毫秒, l, lf, returnValue); } } 转载于:https://www.cnblogs.com/vincedotnet/archive/2007/09/04/881045.html