C#委託(2)

來源:互聯網
上載者:User

筆記來自於《.NET4.0物件導向編程漫談 基礎篇》

Tag:多路委託,泛型委派,Func系列委託、Action系列委託與MethodInvoker、Predicate<T>委託

委託調用列表

委託變數可以組合多個方法並批量執行它們

組合方法:使用加法、減法運算子

Delegate類定義了一個GetInvocationList靜態方法用於擷取委託調用列表,通過這個函數可以瞭解委託的方法集

一個多路委託變數可以引用多個方法,執行一個多路委託變數,會導致它所包含的所有方法被順序執行。

委託變數的內容是“唯讀”的,合并或分割委託列表得到的只是一個新的委託調用列表。

泛型委派:

.NET2.0開始,委託開始支援泛型技術,即泛型委派

一個簡單的泛型委派例子:

        public delegate T MyGenericDelegate<T>(T obj1,T obj2);
        static int MyFunc(int val1,int val2)
        {
            return val1*val2;
        }
        void MainFormLoad(object sender,EventArgs e)
        {
            MyGenericDelegate<int> del;
            del=MyFunc;
            label1.Text=del(12,22).ToString();
        }

可以看到,泛型委派的使用與普通委託類似,不同之處在於使用泛型委派時需要指定泛型參數。

Func系列委託:

Func系列委託的定義:

        public delegate TResult Func<TResult>();
        public delegate TResult Func<T,TResult>(T arg);
        public delegate TResult Func<T1,T2,TResult>(T1 arg1,T2 arg2);
        public delegate TResult Func<T1,T2,T3,TResult>(T1 arg1,T2 arg2,T3 arg3);
        public delegate TResult Func<T1,T2,T3,T4,TResult>(T1 arg1,T2 arg2,T3 arg3,T4 arg4);

Func委託聲明的最後一個泛型型別參數是委託所接收方法的傳回值類型,前面的泛型參數就是委託所接收方法的形參類型

Func系列委託的例子:

        public delegate TResult Func<TResult>();
        public delegate TResult Func<T,TResult>(T arg);
        public delegate TResult Func<T1,T2,TResult>(T1 arg1,T2 arg2);
        public delegate TResult Func<T1,T2,T3,TResult>(T1 arg1,T2 arg2,T3 arg3);
        public delegate TResult Func<T1,T2,T3,T4,TResult>(T1 arg1,T2 arg2,T3 arg3,T4 arg4);
        static int Add(int i,int j){return i+j;}
        static int Multiply(int i,int j){return i*j;}
        static int Process(Func<int,int,int> op,int[] numbers,int from,int to)
        {
            int result=numbers[from];
            for(int i=from;i<=to;i++)
                result=op(result,numbers[i]);
            return result;
        }
        void MainFormLoad(object sender,EventArgs e)
        {
            int[] numbers=new int[7]{0,2,4,1,6,8,10};
            label1.Text=Process(Add,numbers,0,3).ToString()+"\n";
            label1.Text+=Process(Multiply,numbers,3,6).ToString();
        }

定義了多個兩個方法Add和Multiply,和一個數組處理方法Process,它以委託方法作為參數處理數組

Action系列委託與MethodInvoker

Func泛型委派所能接收的方法都有傳回值,Action系列委託是接收返回void的系統預定義委託

public delegate void Action();
public delegate void Action<T>(T obj);
public delegate void Action<T1,T2>(T1 arg1,T2 arg2);
public delegate void Action<T1,T2,T3>(T1 arg1,T2 arg2,T3 arg3);

使用方法和Func一樣

MethodInvoker委託位於System.Windows.Forms中,聲明如下:

public delegate void MethodInvoker();

和無型別參數的Action委託等價,用法也一樣

Predicate<T>委託:

Predicate<T>委託在.NET基底類別庫中經常出現,定義如下:

public delegate bool Predicate<T>(T obj);

此委託引用一個返回bool值的方法,在實際開發中,經常使用Prodicate<T>委託變數引用一個“判斷條件函數”,在判斷條件函數內部書寫代碼錶明函數參數所引用的對象滿足的條件,條件滿足時,函數返回true,一個例子:

        class MyClass
        {
            public int Value;
            public string Info;
        }
        private static List<MyClass> GetMyClassList()
        {
            List<MyClass> lst = new List<MyClass>();
            Random ran = new Random();
            MyClass obj = null;
            for (int i = 0; i < 10; i++)
            {
                obj = new MyClass();
                obj.Value=ran.Next(1,100);
                obj.Info="object "+i.ToString();
                lst.Add(obj);
            }
            return lst;
        }
        static bool GreaterThan50(MyClass elem)
        {
            if (elem.Value > 50)
                    return true;
            return false;
        }
        void MainFormLoad(object sender,EventArgs e)
        {
            Predicate<MyClass> pred = GreaterThan50;
            List<MyClass> lst = GetMyClassList();
           MyClass foundElement= lst.Find(pred);
           if (foundElement != null)
               label1.Text=string.Format("找到了合格對象。Infomation={0},Value={1}", foundElement.Info, foundElement.Value);
           else
               label1.Text="未找到合格對象";
        }

產生一個List<MyClass>,並且尋找其中MyClass對象的Value值大於50的輸出資訊

泛型集合List<T>中定義了一個Find方法:

public T Find(Predicate<T> match);

Lis<T>.Find方法遍曆集合中的所有對象,並將每個對象作為Predicate<T>所引用的“判斷條件函數”實參調用此函數。

使用Predicate<T>委託時,其判斷條件一般是“外部硬性規定的”而非由資料自身指定,否則就不適合採用此類委託。

下節還有匿名方法與Lambda運算式、回調

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.