[英]Encapsulating LINQ select statement
我有看起來像這樣的LINQ語句:
return ( from c in customers select new ClientEntity() { Name = c.Name, ... });
我希望能夠將select抽象到自己的方法中,這樣我可以有不同的“ mapping”選項。 我的方法需要返回什么?
實質上,我希望我的LINQ查詢看起來像這樣:
return ( from c in customers select new Mapper(c));
編輯:
這是用於LINQ to SQL。
現在有新的答案,我注意到這是Linq to SQL ... :)
如果您查看適用於IQueryable<T>
的Select版本,那么它並不需要Func<In, Out>
。 相反,它需要一個Expression<Func<In, Out>>
。 編譯器知道如何從lambda生成這樣的東西,這就是為什么您的常規代碼可以編譯。
因此,要通過將各種傳遞給Select的函數來准備使用各種選擇映射函數,可以這樣聲明它們:
private static readonly Expression<Func<CustomerInfo, string>> GetName = c => c.Name;
private static readonly Expression<Func<CustomerInfo, ClientEntity>> GetEntity = c => new ClientEntity { Name = c.Name, ... };
然后,您將像這樣使用它們:
var names = customers.Select(GetName);
var entities = customers.Select(GetEntity);
您可能必須使用鏈接方法而不是LINQ語法,然后才能傳入您指定的各種Expression
<
Func<TSource, TResult>
>
值中的任何一個:
Expression<Func<CustomerTable, Customer>> someMappingExpression = c => new Customer { Name = c.Name };
return context.CustomerTable.Select(someMappingExpression);
更新:
Select
接受
Func
,而不是
Expression
更新:應該使用的Select
函數確實采用了Expression<Func>
,而不僅僅是Func
。
這是用於linq的對象嗎? 還是對linq感興趣?
因為...選擇新的Mapper(c),因此要求“ c”已經物化為對象,然后傳遞給Mapper()CTor。 (因為在數據庫級別不知道“ c”,而僅在.NET級別知道)
順便說一句:僅當您要在單獨的查詢子句(例如“選擇”)中使用代碼的“分解”部分時,此處介紹的解決方案才有效。 如果您想將它用作還做其他事情的子句的一部分(也許返回帶有其他信息的匿名類型),則需要使用Expression.Xyz方法動態地構建整個表達式樹。
或者,您可以使用此技巧來嵌入我在這里描述的lambda表達式:
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.