前言:
一提到委托,浮現在我們腦海中的大概是聽的最多的就是類似C++的函數指針吧,呵呵,至少我的第一個反應是這樣的。
Func是一種委托,這是在3.5裡面新增的,2.0裡面我們使用委托是用Delegate,Func位于System.Core命名空間下,使用委托可以提升效率,例如在反射中使用就可以彌補反射所損失的性能。
委托是面向對象的程式設計語言中新加入的一種特性,在C#中引入委托使得C#程式的編寫更加靈活。
C#,中可以自己定義各種各樣的委托,但是C#語言也預先為我們定義了兩個做常用的委托,一個是Func一個是Action.
Action< T > 委托
函數最基本的特點就是輸入輸出,即輸入參數-> 執行運算-> 輸出參數,Action是一類沒有輸出參數的委托,但是輸入參數可以為C#中的任意類型,即可以委托執行一下形式的方法。
public void f1(string str, int i)
{
...
}
該函數用Action委托就是:
Action<String, int> do_f1 = f1;
使用時候直接用
do_f1("hello", 12);
Func< T >委托
知道了Action委托,很好了解Func委托,Func委托是由傳回值的委托,其中,輸入參數和傳回值都用泛型表示,例如以下函數的Func委托:
public string f2(int i1, int i2)
{
return (i1+i2).toString();
}
其Func委托為:
Func<int ,int, string> do_f2=f2;
使用的時候直接用:
string result = do_f2(1,2);
一、說明
一般我們定義委托都是有如下兩步:
public delegate void MyDelegate(string name);//定義委托
public MyDelegate myDelegate; //使用委托
但.Net也提供了定義好的委托,我們可以直接使用,比如Func和Action
二、定義
System.Action 無傳回值
Action:
public delegate void Action ();
Action< T >:
public delegate void Action< T > (T obj);
Action< T1, T2 >:
public delegate void Action< T1, T2 > (T1 arg1, T2 arg2);
* delegate void Action<T1,T2,T3,T4>T1 arg1, T2 arg2, T3 arg3, T4 arg4);
System.Func 有傳回值
Func< TResult >
public delegate TResult Func< TResult > ();
Func< T,TResult >
public delegate TResult Func< T, TResult > (T arg);
Func< T1,T2,TResult >
public delegate TResult Func< T1, T2, TResult > (T1 arg1, T2 arg2);
*delegate TResult Func<T1,T2,T3,T4,TResult>T1 arg1, T2 arg2, T3 arg3, T4 arg4);
Predicate隻能接受一個傳入參數,傳回值為bool類型
三、示例了解
例子1:Action
using UnityEngine;
using System.Collections;
using System;
public class ActionTest : MonoBehaviour
{
void Start ()
{
Action action = XXX;
action();
}
void XXX()
{
Debug.Log("100");
}
}
例子2:Action<T>
using UnityEngine;
using System.Collections;
using System;
public class ActionTest : MonoBehaviour
{
void Start ()
{
Action<string> action = XXX;
action("unity C#");
}
void XXX(string name)
{
Debug.Log(name);
}
}
例子3:Action<T1,T2>
using UnityEngine;
using System.Collections;
using System;
public class ActionTest : MonoBehaviour
{
void Start ()
{
Action<string,int> action = XXX;
action("unity C#",100);
}
void XXX(string name,int score)
{
Debug.Log(string.Format("{0} {1}",name,score);
}
}
例子4:Action 直接代理delegate函數體用法
例子4:Action 直接代理delegate函數體用法
#region Action的用法
///Action<T>的用法
///這裡的T為代理函數的傳入類型,無傳回值
Action<string[]> action = delegate(string[] x)
{
var result = from p in x
where p.Contains("s")
select p;
foreach (string s in result.ToList())
{
Console.WriteLine(s);
}
};
string[] str={ "charlies","nancy","alex","jimmy","selina"};
action(str);
Console.ReadKey();
#endregion
上面的例子是通過傳入的String類型的數組,找出其中包含有字元s的項,然後輸出到控制台。
例子5:Func<TResult >
using UnityEngine;
using System.Collections;
using System;
public class FuncTest : MonoBehaviour
{
void Start ()
{
Func< int > func= XXX;
Debug.Log( func() );
}
int XXX()
{
return 10;
}
}
例子6: Func<T,TResult>
using UnityEngine;
using System;
public Class FuncTest:MonoBehaviour
{
void Start()
{
Func<string ,int> func= CallStringLength;
}
int CallStringLength(string str)
{
return str.Lenth;
}
}
例子7: Func<TResult> 直接使用代理delegate函數體
例子7: Func<TResult> 直接使用代理delegate函數體
Func<string> func=delegate()
{
return "我是Func<TResult>委托傳回的結果";
}
例子8:Predicate隻能接受一個傳入參數,傳回值為bool類型,直接使用代理delegate函數體
例子8:Predicate隻能接受一個傳入參數,傳回值為bool類型,直接使用代理delegate函數體
#region Predicate
///bool Predicate<T>的用法
///輸入一個T類型的參數,傳回值為bool類型
Predicate<string[]> predicate = delegate(string[] x)
{
var result = from p in x
where p.Contains("s")
select p;
if (result.ToList().Count > 0)
{
return true;
}
else
{
return false;
}
};
string[] _value = { "charlies", "nancy", "alex", "jimmy", "selina" };
if (predicate(_value))
{
Console.WriteLine("They contain.");
}
else
{
Console.WriteLine("They don't contain.");
}
Console.ReadKey();
#endregion
上面的代碼其實也是判斷String數組中有沒有包含s的項,有的話就在控制台列印出 They contain.沒有的話就列印出They don't contain