我是linq的新手。我需要运行一个连接两列的查询(AnonymousUser.AnonymousId
为uniqueidentifier
而comment.UserId为nvarchar(100)
),如下所示:
using (CommentEntities db = new CommentEntities())
{
// filteredComments is a query that is not run until the next .ToList()
IQueryable<Comment> filteredComments = this.CommentGetList(...);
var query = from comment in filteredComments
// following line is the syntax error, because columns' types don't match
join user in db.AnonymousUsers on comment.UserId equals user.AnonymousId into gj
from userNull in gj.DefaultIfEmpty()
select new CommentWithName
{
Comment = comment,
UserId = comment.UserId,
FirstName = (userNull == null ? "" : userNull.Name),
LastName = "",
Email = (userNull == null ? "" : userNull.Email)
};
return query.ToList();
}
首先,我很高兴用.ToString()
编写查询!事实证明,实体框架不知道如何将其转换为sql。 Guid.Parse(string)
也是如此。此外,new Guid(string)
不能在linq中用于实体(仅允许无参数构造函数)!
所以在搜索之后,我发现在EF 4.0中做这样的事情是不可能的!我将我的代码迁移到了一个我并不高兴的存储过程。
是否可以告诉实体框架在SQL中使用CAST
?
这个问题有什么解决方案吗?有什么方法可以把代码中的逻辑带来吗?
注意:我打算在一个GO 中执行此操作。否则,一种可能的解决方案是从第一个表中获取实体,并将Ids放入列表中并从第二个表中获取实体。
答案 0 :(得分:0)
在应用这些方法之前调用toList()。像:
var Product = db.Products.Where(p => p.ProductId == Guid.Parse("B4E913F9-166C-49BA-AADE-6DB889D1756F")).Single();
会抛出一个
c#LINQ to Entities无法识别方法“System.Guid Parse”(System.String)'方法,而且此方法无法转换为商店表达式
但这有效:
var Product = db.Products.ToList().Where(p => p.ProductId == Guid.Parse("B4E913F9-166C-49BA-AADE-6DB889D1756F")).Single()
p.s:我认为你会丢失延迟加载,但你可以在调用.ToList()之前用.Include进行eagerloading。
答案 1 :(得分:0)
如果您的list
是对象列表,则可以将其转换为具有Guid作为标识符的类型,首先创建新的匿名类型,然后根据UserId
对其进行过滤,确保UserId
属于int
类型,不包括在join:
int output = 0;
var secondList = list.Where(x=>!int.TryParse(x.UserID, out output))
.Select(x=>new {Comment = x, ID = new Guid(x.UserID))
.ToList();
现在,您可以使用secondList
。