你真的應該在你的代碼上做一個轉到定義。使用LINQ到SQL和實體框架的function是
IQueryable<TSource> Where<TSource>(this IQueryable<TSource> source, Expression<Func<TSource, bool>> predicate)
包含在使用expression trees的System.Linq.Queryable,是能夠「描繪」的代碼段一constuct。小報價:
表達式樹表示代碼在類似樹的數據結構,其中每個節點是一個表達,例如,一個方法調用或二進制操作例如x <年。
例如,你的第一個表達
var products = context.Products.Where(p => p.Location == "France");
是由C#編譯器轉換爲這樣的代碼:
ParameterExpression par = Expression.Parameter(typeof(Product), "p");
LambdaExpression lambda = Expression.Lambda(
Expression.Equal(
Expression.Property(par, "Location"),
Expression.Constant("France")),
par);
var products = context.Products.Where(lambda);
現在......而一個表達式樹的創建非常簡單,反向操作(去構建表達式樹並創建查詢)是非常非常複雜的事情。大頭痛複雜。近乎神奇的複合體:-)
問題不在於構建表達式樹。這很容易。你使用ExpressionVisitor,你就完成了。問題在於合併LINQ查詢的各個層次並理解程序員想要獲得什麼。
我會補充一點,IL(.NET的「彙編」)足夠高,可以反編譯它(參見例如IlSpy)。至少有一個庫,DelegateDecompiler能夠將委託編譯到表達式樹中,所以即使沒有表達式樹,LINQ到SQL和EF也可以直接使用類似和反編譯的方法到SQL語言。