.Net的異步機制(委托Delegate) - STEP 1

作者: Andy Huang  來源: 博客園  發布時間: 2008-12-29 15:04  閱讀: 5136 次  推薦: 0   原文鏈接   [收藏]  
 
摘要:.Net異步機制,包括簡單的委托知識
[1] .Net的異步機制(委托Delegate) - STEP 1
[2] .Net的異步機制(委托Delegate) - STEP 1

  在閱讀下面知識前,我已經認為你已經具有c#的基礎,包括簡單的委托知識; 代碼使用VS2008開發,但是會在.Net Framework 2.0(C Sharp)編寫

什么是.Net異步機制呢?

  在解釋這個話題前,我們先看看同步的程序,就是我們常用的Hello World 程序。

Code 1:

 1    class Program
 2    {
 3        static void Main(string[] args)
 4        {
 5            // 查看當前的線程ID, 是否線程池里面的線程
 6            Console.WriteLine("1,Thread ID:#{0},Is PoolThread?{1}",
Thread.CurrentThread.ManagedThreadId, Thread.CurrentThread.IsThreadPoolThread);

 7
 8            AsyncTest test = new AsyncTest();
 9            string val = test.Hello("Andy Huang");
10
11            Console.WriteLine(val);
12            Console.ReadLine(); // 讓黑屏等待,不會直接關閉..
13        }
14    }
15
16    public class AsyncTest
17    {
18        public string Hello(string name)
19        {
20            // 查看當前的線程ID, 是否線程池里面的線程
21            Console.WriteLine("2,Thread ID:#{0},Is PoolThread?{1}",
Thread.CurrentThread.ManagedThreadId, Thread.CurrentThread.IsThreadPoolThread);

22            return "Hello:" + name;
23        }
24    }

 

1

  我們可以從圖1看出,我們平常寫的Hello 程序是同一個線程的,而且不是線程池理的線程程序。按照上面的程序稍做改動, 那么開始我們第一個異步的Hello World 程序。

  使用.Net 的委托機制來為我們的程序提供異步操作行為

  1, 為我們的AsyncTest(Hello方法) 聲明一個委托

  public delegate string AsyncEventHandler(string name);

  2,使用委托提供的BeginInvoke, EndInvoke 方法(具體使用下一篇文章詳細介紹)來提供異步的調用

string val = test.Hello("Andy Huang");

修改為

AsyncEventHandler async = test.Hello;

    IAsyncResult result = async.BeginInvoke("Andy Huang", null, null);

    string val = async.EndInvoke(result);

下面是完整的代碼.

Code 2:

 1    class Program
 2    {
 3        static void Main(string[] args)
 4        {
 5            // 查看當前的線程ID, 是否線程池里面的線程
 6            Console.WriteLine("1,Thread ID:#{0},Is PoolThread?{1}",
Thread.CurrentThread.ManagedThreadId, Thread.CurrentThread.IsThreadPoolThread);

 7
 8            AsyncTest test = new AsyncTest(); 
 9            //把Hello 方法分配給委托對象
10            AsyncEventHandler async = test.Hello; //注釋1,建議用=,不用+=
11
12            //發起一個異步調用的方法,賦值"Andy Huang", 返回IAsyncResult 對象
13            IAsyncResult result = async.BeginInvoke("Andy Huang"nullnull);
14
15            //這里會阻礙線程,直到方法執行完畢
16            string val = async.EndInvoke(result);
17
18            Console.WriteLine(val);
19            Console.ReadLine(); // 讓黑屏等待,不會直接關閉..
20        }
21    }
22
23    //我們使用委托來提供.Net的異步機制
24    public delegate string AsyncEventHandler(string name);
25    public class AsyncTest
26    {
27        public string Hello(string name)
28        {
29            // 查看當前的線程ID, 是否線程池里面的線程
30            Console.WriteLine("2,Thread ID:#{0},Is PoolThread?{1}",
Thread.CurrentThread.ManagedThreadId, Thread.CurrentThread.IsThreadPoolThread);

31            return "Hello:" + name;
32        }
33    }

 

注釋1: =操作符在于分配委托對象時候不需要初始化;并且異步調用時候只能有一個目標方法.

2

  對比圖1 和圖2, ,可以看出(2,Thread ID:#10,Is PoolThread?True),在使用異步機制的時候,其實就是開啟一個新的線程來執行我們的方法,并且這個線程來自 線程堆. 到這里,我們就很好的解釋了什么是.Net異步機制?”

說到這里,結束了嗎? 可能大家會想其實使用異步就是多了個委托( public delegate string AsyncEventHandler(string name);) 那么到底為我們做了些什么呢?

  通過反編譯(微軟提供的IL Disassembler)我們看到

3

編譯器為我們生成了下面類定義(其實委托就是一個類)

Code 3

public sealed class AsyncEventHandler : MulticastDelegate

    {

        public AsyncEventHandler(object @object, IntPtr method)

        {....}

        public virtual IAsyncResult BeginInvoke(string name, AsyncCallback callback, object @object)

        {...}

        public virtual string EndInvoke(IAsyncResult result)

        {...}

        public virtual string Invoke(string name)

        {...}

    }

繼承于MulticastDelegate, 提供了BeginInvoke / EndInvoke / Invoke.

Invoke 是我們Code 1 同步調用的方法,當然我們也可以直接使用Invoke來同步調用.

BeginInvoke / EndInvoke Code 2中使用的異步調用的方法,下篇文章我會詳細介紹

 

[第1頁][第2頁]
0
0
 
 
 

文章列表

全站熱搜
創作者介紹
創作者 大師兄 的頭像
大師兄

IT工程師數位筆記本

大師兄 發表在 痞客邦 留言(0) 人氣()