Lambda表達式可分為表達式lambda和語句lambda
表達式lambda:表達式位於 => 運算符右側的lambda表達式稱為表達式lambda
(input parameters) => expression //表達式lambda
例如
(x, y) => x == y
語句lambda:=> 運算符右側是一個語句塊,語句包含在大括號中
(input parameters) => {statement;} //語句lambda
例如:
(x, y) => {return x == y;}
這兩者除了寫法不一樣,還有什么區別嗎,用以下代碼作為測試
using System; using System.Collections.Generic; namespace LinqTest { class Program { static void Main(string[] args) { List<int> list = new List<int> { 1, 3, 2, 4 }; var resultUsingExpressionLambda = list.FindAll(p => p < 3); Console.WriteLine("使用表達式lambda:"); foreach (var item in resultUsingExpressionLambda) { Console.WriteLine(item); } var resultUsingStatementLambda = list.FindAll(p => { return p < 3; }); Console.WriteLine("使用語句lambda:"); foreach (var item in resultUsingStatementLambda) { Console.WriteLine(item); } } } }
代碼比較簡單,就是分別使用表達式lambda和語句lambda找出小於3的數,然后輸出來,結果如下
輸出結果一樣。
查看反編譯后的代碼
看來編譯器做了處理,兩者的代碼都是一樣了,既然這樣,那么在語句lambda中多加一行代碼,Console.WriteLine(p); 這樣就不會生成一樣的代碼了
Console.WriteLine(p.ToString());
using System; using System.Collections.Generic; namespace LinqTest { class Program { static void Main(string[] args) { List<int> list = new List<int> { 1, 3, 2, 4 }; var resultUsingExpressionLambda = list.FindAll(p => p < 3); Console.WriteLine("使用表達式lambda:"); foreach (var item in resultUsingExpressionLambda) { Console.WriteLine(item); } var resultUsingStatementLambda = list.FindAll(p => { Console.WriteLine(p);//這是新加的 return p < 3; }); Console.WriteLine("使用語句lambda:"); foreach (var item in resultUsingStatementLambda) { Console.WriteLine(item); } } } }
再查看反編譯后的代碼
再來看下IL代碼
可以看到,無論是表達式lambda還是語句lambda,最后都生成一個方法,這里生成的方法分別是和
,然后將方法賦給委托變量,就是這部分:
所以,給委托變量賦值時,表達式lambda和語句lambda寫法不一樣,但是最后編譯器都生成一個方法。
還有個不同點,表達式lambda可以轉換為類型Expression<T>的表達式樹,而語句lambda不可以
Expression<Func<int, int, int>> expression = (a, b) => a + b;//正確 Expression<Func<int, int, int>> expression1 = (a, b) => { return a + b; };//錯誤,無法將具有語句體的 lambda 表達式轉換為表達式樹