LINQ to Entities无法识别方法'System.Linq.IQueryable`

时间:2013-09-13 14:27:34

标签: c# .net linq entity-framework

我想运行这个LINQ简单代码,在LINQ中有记录号,但结果是错误

var model = _db2.Persons.Select(
    (x, index) => new 
    {
        rn = index + 1,
        col1 = x.Id
    }).ToList();

错误:

  

LINQ to Entities无法识别该方法   “System.Linq.IQueryable 1[<>f__AnonymousType2 2       [System.Int32,System.Int32]]选择[Person,&lt;&gt; f__AnonymousType2 2](System.Linq.IQueryable 1       [MvcApplication27.Models.Person],System.Linq.Expressions.Expression 1[System.Func 3       [MvcApplication27.Models.Person,System.Int32,&LT;&GT; f__AnonymousType2`2       [System.Int32,System.Int32]]])'方法,并且此方法无法转换为商店       表达

2 个答案:

答案 0 :(得分:22)

问题是LINQ to Entities不了解如何将Select重载(提供索引的重载)转换为SQL查询。您可以通过首先从所需的数据库中选择部分来解决此问题(避免不必要地选择每一列),然后执行AsEnumerable()将其作为IEnumerable<T>而不是IQueryable<T>,并且然后纯粹用C#做Select(简而言之,IQueryable<T>转换为SQL,而IEnumerable<T>则在代码中运行。

var model = _db2.Persons.Select(x => x.Id).AsEnumerable().Select(
    (id, index) => new
    {
        rn = index + 1,
        col1 = id
    }).ToList();

请注意,您拥有的查询似乎是无序的,因此每次调用时,id / index配对都会更改。如果您期望一致性,则应按某种方式订购(例如_db2.Persons.OrderBy(...))。

修改

Scott添加评论:

  

作为一个很好的参考here is the list of all Linq statements built in to the framework and a listing if it is compatible or not

答案 1 :(得分:1)

您可以选择Id,然后使用linq to objects创建自己的匿名对象,样本:

var model = _db2.Persons.Select(x => x.Id)
                        .ToList() // return int[]
                        .Select((id, index) => new
                                {
                                    rn = index + 1,
                                    col1 = id
                                 }) // return anonymous[] (with rn and col1)
                         .AsEnumerable(); // get an IEnumerable (readonly collection)

可能这是因为实体框架不支持使用linq的这种查询,因为linq可以在内存中执行,因此,在这种情况下,您可以选择只需要(在您的情况下为id)并执行它,使用ToList()方法使您的查询具体化,然后您将在内存中有一个列表,因此,您可以使用linq到对象并使用所需的支持方法。