1. 程式人生 > >C# 多線程之異步回調

C# 多線程之異步回調

clean leg 多線程 pan ons sync line lee 回調

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Remoting.Messaging;
using System.Text;
using System.Threading;

namespace yibu
{
    public delegate int AddHandler(int a,int b);
    public class CAdd
    {
        public static int Add(int a, int b)
        {
            Console.WriteLine(
"開始計算..."); Console.WriteLine("當前線程ID:" + Thread.CurrentThread.ManagedThreadId); Thread.Sleep(4000); Console.WriteLine("計算完成"); return a + b; } } class Program { void cleanup(int result) { Console.WriteLine("調用者繼續工作
"); Console.WriteLine(result); Console.ReadKey(); } static void sync_call() { Console.WriteLine("Sync_call_test"); AddHandler handler = new AddHandler(CAdd.Add); int result = handler.Invoke(1, 2); Console.WriteLine(
"調用者繼續工作"); Console.WriteLine(result); Console.ReadKey(); } static void async_call() { Console.WriteLine("Async_call_test"); AddHandler handler = new AddHandler(CAdd.Add); IAsyncResult result = handler.BeginInvoke(1, 2, null, null); Console.WriteLine("調用者繼續工作"); Console.WriteLine(handler.EndInvoke(result)); Console.ReadKey(); } static void async_callback() { Console.WriteLine("Async_callback_test"); AddHandler handler = new AddHandler(CAdd.Add); IAsyncResult result = handler.BeginInvoke(1, 2, new AsyncCallback(mycall), "AsyncState:OK"); Console.WriteLine("調用者繼續工作"); //Console.ReadKey(); } static void Main() { Console.WriteLine("主線程ID:" + Thread.CurrentThread.ManagedThreadId); async_callback(); Console.WriteLine("happy coding,yes"); Thread.Sleep(44000); Console.WriteLine("Continue Happy coding"); Thread.Sleep(2000); Console.ReadKey(); } static void mycall(IAsyncResult result) { Console.WriteLine("where am i?"); Console.WriteLine("當前線程ID:" + Thread.CurrentThread.ManagedThreadId); AddHandler handler = (AddHandler)((AsyncResult)result).AsyncDelegate; Console.WriteLine(handler.EndInvoke(result)); Console.WriteLine(result.AsyncState); } } }

代碼中主函數使用的是異步回調,為了說明其優越性,代碼提供了

其他兩種方法來做比較:

1.同步調用,代碼在sync_call函數中,

這個其實還是本線程調用,和調用個函數沒區別。

2.異步調用

在async_call函數中,調用完handler.BeginInvoke 之後,主線程會繼續往下執行,

但是在handler.EndInvoke的時候,如果任務沒有完成,還是會阻塞在這裏。

註意使用異步回調的核心代碼:

IAsyncResult result = handler.BeginInvoke(1, 2, new AsyncCallback(mycall), "AsyncState:OK");

第三個參數註冊回調函數,第三個傳遞一個object對象。

回調函數mycall在任務線程裏面執行,

AddHandler handler = (AddHandler)((AsyncResult)result).AsyncDelegate;來獲取委托對象,然後再

handler.EndInvoke(result) 返回值。

在回調函數中獲取主線程的委托對象還可以使用如下方法:

在BeginInvoke的時候將 ,委托對象傳到第四個參數,

回調函數中使用result.AsynState 再轉成(AddHandler)

AddHandler handler = (AddHandler)(result.AsyncState);

C# 多線程之異步回調