利用委托实现异步调用

  1. 同步调用示例(委托是一个类型安全的,面向对象的指针)

    using System;
    using System.Threading;
    
    namespace Demo
    {
        public delegate int Operate(int x, int y);
    
        public class DelegateAsync
        {
            static int Add(int a, int b)
            {
                Console.WriteLine ("Add() invoked on thread:{0}\n",
                    Thread.CurrentThread.GetHashCode ());
                Thread.Sleep (5000);
                return a + b;
            }
    
            static void Main()
            {
                Console.WriteLine ("Main() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Add() call in Synchronouse mode
                Operate op = new Operate (Add);
                int answer = op (10, 20);
                //after Add() executed, the folow goes on.
                Console.Write("After Add() executed, result = {0}",answer);
                Console.ReadKey ();
            }
        }
    }
    剖析代码的继承关系: 代理Operate经历了3次派生(绿色部分),实现了一个构造和3个虚拟函数(黄色部分).

  2. 异步调用方法:线程异步了,但是主线程等待次线程返回才能获得结果,阻塞在EndInvoke上.

    using System;
    using System.Threading;
    
    namespace Demo
    {
        public delegate int Operate(int x, int y);
    
        public class DelegateAsync
        {
            static int Add(int a, int b)
            {
                Console.WriteLine ("Add() invoked on thread:{0}\n",
                    Thread.CurrentThread.GetHashCode ());
                Thread.Sleep (5000);
                return a + b;
            }
    
            static void Main()
            {
                Console.WriteLine ("Main() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Add() call in Synchronouse mode
                Operate op = new Operate (Add);
                IAsyncResult result = op.BeginInvoke(10,20,null,null);
                Console.WriteLine ("Doing more in Main() exected immediately.");
                //the thread susppend on EndInvoke while ‘result‘ is ready!
                int answer = op.EndInvoke (result);
                Console.Write("After Add() executed, result = {0}",answer);
                Console.ReadKey ();
            }
        }
    }
  3. 同步调用:如果线程没有返回,不要一直问何时返回,每间隔500ms做该做的事情!!!
    using System;
    using System.Threading;
    
    namespace Demo
    {
        public delegate int Operate(int x, int y);
    
        public class DelegateAsync
        {
            static int Add(int a, int b)
            {
                Console.WriteLine ("Add() invoked on thread:{0}\n",
                    Thread.CurrentThread.GetHashCode ());
                Thread.Sleep (5000);
                return a + b;
            }
    
            static void Main()
            {
                Console.WriteLine ("Main() invoked on thread:{0}\n",
                    Thread.CurrentThread.GetHashCode ());
                //Add() call in Synchronouse mode
                Operate op = new Operate (Add);
                IAsyncResult result = op.BeginInvoke(10,20,null,null);
                //while result is not OK, do it every 500 ms.
                while (!result.AsyncWaitHandle.WaitOne(500,true)) {//result.IsCompleted
                    Console.WriteLine ("Doing more work in Main().");
                }
                int answer = op.EndInvoke (result);
                Console.Write("After Add() executed, result = {0}",answer);
                Console.ReadKey ();
            }
        }
    }
  4. 线程回调: 好吧,干脆你返回的时候通知我,我该干啥不耽搁!
    using System;
    using System.Threading;
    
    /// <summary>
    /* Main() invoked on thread:1
    Main() execute no need to wait any more.
    Add() invoked on thread:3
    AddComplete() invoked on thread:3
    Your Addition is complete.
    */
    /// </summary>
    namespace Demo
    {
        public delegate int Operate(int x, int y);
    
        public class DelegateAsync
        {
            static int Add(int a, int b)
            {
                Console.WriteLine ("Add() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                Thread.Sleep (5000);
                return a + b;
            }
    
            static void AddComplete(IAsyncResult ia)
            {
                Console.WriteLine ("AddComplete() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Get Result value
                System.Runtime.Remoting.Messaging.AsyncResult ar=
                    (System.Runtime.Remoting.Messaging.AsyncResult)ia;
                Operate op = (Operate)ar.AsyncDelegate;
                Console.WriteLine ("The value is {0}.", op.EndInvoke (ia));
            }
    
            static void Main()
            {
                Console.WriteLine ("Main() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Add() call in Synchronouse mode
                Operate op = new Operate (Add);
                IAsyncResult result = op.BeginInvoke (10, 20, new AsyncCallback (AddComplete), null);
                Console.WriteLine ("Main() execute no need to wait any more.");
                Console.ReadKey ();
            }
        }
    }
  5. 主线程向次线程传递对象,通知!
    using System;
    using System.Threading;
    
    /// <summary>
    /*

    Main() invoked on thread:1
    Main() execute no need to wait any more.
    Add() invoked on thread:3
    AddComplete() invoked on thread:3
    The value is 30.
    The Main() thread is :1

    */
    /// </summary>
    namespace Demo
    {
        public delegate int Operate(int x, int y);
    
        public class DelegateAsync
        {
            static int Add(int a, int b)
            {
                Console.WriteLine ("Add() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                Thread.Sleep (5000);
                return a + b;
            }
    
            static void AddComplete(IAsyncResult ia)
            {
                Console.WriteLine ("AddComplete() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Get Result value
                System.Runtime.Remoting.Messaging.AsyncResult ar=
                    (System.Runtime.Remoting.Messaging.AsyncResult)ia;
                Operate op = (Operate)ar.AsyncDelegate;
                Console.WriteLine ("The value is {0}.", op.EndInvoke (ia));
                Thread thread = (Thread)ia.AsyncState;
                Console.WriteLine ("The Main() thread is :{0}", thread.GetHashCode());
            }
    
            static void Main()
            {
                Console.WriteLine ("Main() invoked on thread:{0}",
                    Thread.CurrentThread.GetHashCode ());
                //Add() call in Synchronouse mode
                Operate op = new Operate (Add);
                IAsyncResult result = op.BeginInvoke (10, 20,
                    new AsyncCallback (AddComplete),Thread.CurrentThread);
                Console.WriteLine ("Main() execute no need to wait any more.");
                Console.ReadKey ();
            }
        }
    }

推荐下博客客户端工具: Download

时间: 2024-10-10 16:05:49

利用委托实现异步调用的相关文章

C#委托的异步调用

#委托的异步调用本文将主要通过"同步调用"."异步调用"."异步回调"三个示例来讲解在用委托执行同一个"加法类"的时候的的区别和利弊.   首先,通过代码定义一个委托和下面三个示例将要调用的方法: /*添加的命名空间using System.Threading;using System.Runtime.Remoting.Messaging;*/    public delegate int AddHandler(int a,i

C#委托的异步调用1

本文将主要通过“同步调用”.“异步调用”.“异步回调”三个示例来讲解在用委托执行同一个“加法类”的时候的的区别和利弊. 首先,通过代码定义一个委托和下面三个示例将要调用的方法: /*添加的命名空间using System.Threading;using System.Runtime.Remoting.Messaging;*/    public delegate int AddHandler(int a,int b);    public class 加法类    {        public

c# 委托与异步调用

背景:在winform UI中,有时需要对控件进行比较频繁的刷新,如进度条.picturebox显示视频等.如果在主线程进行这些刷新操作,操作还未完成就将执行下一次刷新,程序将发生错误:如果只是创建另一个线程执行这些操作,将和主线程产生竞争,造成界面锁死(因此windows GUI编程有一个规则,就是只能通过创建控件的线程来操作控件的数据,否则就可能产生不可预料的结果).这时候,我们就可以用委托与异步来解决这个问题. 委托:回顾一下委托 ,一.定义委托,委托定义的参数与传递给委托的方法的参数一致

异步和多线程,委托异步调用,Thread,ThreadPool,Task,Parallel,CancellationTokenSource

1 进程-线程-多线程,同步和异步2 异步使用和回调3 异步参数4 异步等待5 异步返回值 5 多线程的特点:不卡主线程.速度快.无序性7 thread:线程等待,回调,前台线程/后台线程, 8 threadpool:线程池使用,设置线程池,ManualResetEvent9 Task初步接触 10 task:waitall waitany continueWhenAny continueWhenAll  11并行运算Parallel 12 异常处理.线程取消.多线程的临时变量和lock13 A

C# 委托的三种调用示例(同步调用 异步调用 异步回调)

本文将主要通过同步调用.异步调用.异步回调三个示例来讲解在用委托执行同一个加法类的时候的的区别和利弊 首先,通过代码定义一个委托和下面三个示例将要调用的方法: public delegate int AddHandler(int a,int b); public class 加法类 { public static int Add(int a, int b) { Console.WriteLine("开始计算:" + a + "+" + b); Thread.Slee

C# 委托的同步调用和异步调用

委托的Invoke方法用来进行同步调用.同步调用也可以叫阻塞调用,它将阻塞当前线程,然后执行调用,调用完毕后再继续向下进行. 同步调用的例子: using System; using System.Threading; public delegate int AddHandler(int a, int b); public class Foo { static void Main() { Console.WriteLine("**********SyncInvokeTest***********

客户端的异步调用

C#客户端的异步操作 阅读目录 开始 示例项目介绍 同步调用服务 异步接口介绍 1. 委托异步调用 2. 使用IAsyncResult接口实现异步调用 3. 基于事件的异步调用模式 4. 创建新线程的异步方式 5. 使用线程池的异步方式 6. 使用BackgroundWorker实现异步调用 客户端的其它代码 各种异步方式的优缺点 异步文件I/O操作 数据库的异步操作 异步设计的使用总结 在Asp.net中使用异步 上篇博客[用Asp.net写自己的服务框架] 我讲述了如何实现自己的服务框架,但

一位牛人的多线程和异步调用文章

转自小顾问原文 一位牛人的多线程和异步调用文章 首先申明:这篇文章不是我写的,我看到的一位牛人的,自己慢慢的消化了…… 摘要:本章讨论与智能客户端应用程序中多线程的使用有关的问题.为了最大限度地提高智能客户端应用程序的响应能力,需要仔细考虑如何和何时使用多线程.线程可以大大提高应用程序的可用性和性能,但是当您确定它们将如何与用户界面交互时,需要对其进行非常仔细的考虑. 线程是基本执行单元.单线程执行一系列应用程序指令,并且在应用程序中从头到尾都经由单一的逻辑路径.所有的应用程序都至少有一个线程,

.NET委托解析(异步委托)

上一篇我们了解到了,委托的基本感念,列举了几个委托的实例,并根据实例来反编译源码查看.NET 委托的内部实现,从浅入深的角度来详细的去解析委托的实质,本文将系上篇继续讨论异步委托的实现以及异步委托的源码解析. 首先本文只会从委托的层面的去编写,不会涉及到深层次的异步.(后续的系列中将会对异步进行深入讲解.敬请关注.). 委托的异步调用方式 在上一篇中我们在实例中是直接通过委托对象的,例如: private static void Main(string[] args)  {        Pro