委託,匿名方法,λ 運算式

來源:互聯網
上載者:User

1、委託:委託本質上就是函數指標,但由於指標過於靈活,因此在很多語言中都採用了更加安全的替代類型,比如Delphi的對象方法和C#的委託.委託使得方法可以做為參數進行傳遞,極大的方便了程式的處理(事件本質上就是委託,是委託的一種典型應用)。使用委託的最大好處一是可以實現演算法上的分離,二是可以實現一定程度上的動態聯編(即物件導向中的所謂多態),對於演算法上的分離,在物件導向的模式設計中,策略模式是比較典型的,其實我們使用委託照樣可以在一定程度上模仿其功能,實際上使用原則模式在很多時候還不如委託來得簡單有效,而且在效能上也比委託差些。由於委託本身也是一種規範和標準,因此在這種層面上和抽象類別,介面一樣具有多態性。當然,委託的這種多態性也必須遵循程式設計語言的繼承規範:子類執行個體可以賦給父類變數,反之則不允許。根據這種規範,站在委託的角度,委託具有傳回值協變,參數抗變的特性。即實際委託調用的傳回值只能是委託定義的傳回值類型的子類,實際調用方法的參數必須是委託定義中的參數的父類。     

      如: public delegate A Compare(Type1 v);

     實際調用的方法:public B CompareInstance(Type2 v).根據繼承規範,Type2必須是Type1的父類,而B必須是A的子類.

    

2、匿名方法:在給委託變數執行個體化的時候,一般是提供一個有名的方法,如:Compare _compare=CompareInstance;但現在C#提供了一種匿名方法,匿名方法是一個代碼塊,本質上與命名方法沒有什區別,但與命名方法相比,提供了如下兩個便利:1是書寫上,使得委託變數可以與執行個體化方法在一起,這樣有利於理解;2是匿名方法可以訪問匿名方法代碼塊以外的變數,這點上相對於命名方法要靈活很多,這是優點,也是缺點,缺點是其破壞了代碼的封裝性,當然,你把匿名方法與其所在的代碼模組看作是一個整體(如果從邏輯上來講也確實是個整體),那麼這個缺點就無所謂了。下面是簡單的例子:

      int theTest=0; 

     Compare _compare = delegate(int v){

          theTest ++;

       }

     _compare(2);//調用.

     匿名方法使用上的限制主要是程式控制方面的,比如不能跳轉到匿名方法塊外部,也不能從外部跳轉到匿名方法塊內部等。由於這種匿名代碼塊並不能複用,因此我覺得匿名方法的實際應用價值並不大,何況還可以用λ運算式替代。

3、λ運算式:λ運算式的作用其實跟匿名方法沒什麼區別,可以將λ運算式理解成匿名方法的一種簡潔表達方式。

     匿名方法和λ運算式的引入,主要作用在於可以使得程式的表達更加簡潔,但把這兩個東西作為C#語言一個新的特徵就有那麼一點王婆賣瓜的味道了.其實所謂的範型、匿名方法等很多所謂的C#的新東西都是從C++中拿來重新封裝一下而已,思想上並沒有本質的進步(題外話:我們中國程式員很多時候都是被這種似是而非的新技術驅趕著跑)。

下面是一個簡單的測試例子:

private void button1_Click(object sender, EventArgs e)
        {

                  //Teacher是一個類,包含部門id和姓名兩個欄位.
            var teachers = TestDataMgt.GetTeachers();//擷取一個Teacher列表.
            //一般方法(委託的典型調用方式),Select需要一個委託參數,該委託的定義:

                  //Func<TSource,TResult>(TSource obj)
            //var depts2 = teachers.Select(new Func<Teacher,int>(FuncB)).Distinct();
            #region 使用匿名方法調用.
            //Func<Teacher, int> bb = delegate(Teacher T)
            //{
            //    return T._deptId;
            //};
            //var depts2 = teachers.Select(bb).Distinct();
            #endregion

                  //使用λ運算式,非簡潔方式

                   //var depts2 = teachers.Select((T) => { return T._deptId; }).Distinct();
            //等價於
            var depts2 = teachers.Select(T=>T._deptId).Distinct();
            foreach (var el in depts2)
            {
                this.richTextBox2.Text += el.ToString() + "/r/n";
            }
        }
        private int FuncB(Teacher obj)
        {
            return obj._deptId;
        }

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.