LINQ to Entities不识别方法System.String Format(System.String,System.Object,System.Object)'

我有这个linq查询:

private void GetReceivedInvoiceTasks(User user, List<Task> tasks) { var areaIds = user.Areas.Select(x => x.AreaId).ToArray(); var taskList = from i in _db.Invoices join a in _db.Areas on i.AreaId equals a.AreaId where i.Status == InvoiceStatuses.Received && areaIds.Contains(a.AreaId) select new Task { LinkText = string.Format(Invoice {0} has been received from {1}, i.InvoiceNumber, i.Organisation.Name), Link = Views.Edit }; } 

它有问题,但。 我正在尝试创build任务。 对于每一个新的任务,当我把链接文本设置为一个像“你好”这样的常量string时,它就没有问题。 然而,上面我试图使用发票的属性来build立属性linktext。

我得到这个错误:

base {System.SystemException} = {“LINQ to Entities不能识别方法System.String Format(System.String,System.Object,System.Object)'方法,并且此方法不能被转换成存储expression式。 }

任何人知道为什么 任何人都知道这样做的另一种方式,使其工作?

entity framework试图在SQL方面执行您的投影,没有等同于string.Format 。 使用AsEnumerable()来强制对Linq的对象进行评估。

根据以前的答案,我已经给你我会重组你的查询是这样的:

 int statusReceived = (int)InvoiceStatuses.Received; var areaIds = user.Areas.Select(x=> x.AreaId).ToArray(); var taskList = (from i in _db.Invoices where i.Status == statusReceived && areaIds.Contains(i.AreaId) select i) .AsEnumerable() .Select( x => new Task() { LinkText = string.Format("Invoice {0} has been received from {1}", x.InvoiceNumber, x.Organisation.Name), Link = Views.Edit }); 

我也看到你在查询( Organisation.Name )中使用相关的实体,确保你添加适当的Include到您的查询,或具体实现这些属性供以后使用,即:

 var taskList = (from i in _db.Invoices where i.Status == statusReceived && areaIds.Contains(i.AreaId) select new { i.InvoiceNumber, OrganisationName = i.Organisation.Name}) .AsEnumerable() .Select( x => new Task() { LinkText = string.Format("Invoice {0} has been received from {1}", x.InvoiceNumber, x.OrganisationName), Link = Views.Edit }); 

IQueriable从IEnumerable中派生出来,主要的相似之处在于,当你将查询发送到数据库引擎时,这个简单的时刻就是告诉C#处理服务器上的数据(而不是客户端)或告诉SQL处理数据。

所以基本上当你说IEnumerable.ToString()时,C#获取数据集合并在对象上调用ToString()。 但是当你说IQueriable.ToString()C#告诉SQL调用对象的ToString(),但在SQL中没有这样的方法。

缺点是在C#中处理数据时,在C#应用filter之前,必须在内存中构build整个您正在查看的集合。

最有效的方法是使用您可以应用的所有filter将查询设置为IQueriable。

然后在内存中构build它,并在C#中进行数据格式化。

 IQueryable<Customer> dataQuery = Customers.Where(c => c.ID < 100 && c.ZIP == 12345 && c.Name == "John Doe"); var inMemCollection = dataQuery.AsEnumerable().Select(c => new { c.ID c.Name, c.ZIP, c.DateRegisterred.ToString("dd,MMM,yyyy") });