我有两个数据库表 Contact (Id, Name, ...) 和 ContactOperationalPlaces (ContactId, MunicipalityId),其中一个联系人可以连接到多个 ContactOperationalPlaces。
我正在尝试做的是使用 IQueryable 构建一个查询(ASP .NET、C#),该查询仅选择存在于 ContactOperationalPlaces 表中的所有具有给定 MunicipalityId 的联系人。
sql 查询如下所示:
select * from Contacts c
right join ContactOperationPlaces cop on c.Id = cop.ContactId
where cop.MunicipalityId = 301;
使用 linq 它看起来像这样:
//_ctx is the context
var tmp = (from c in _ctx.Contacts
join cop in _ctx.ContactOperationPlaces on c.Id equals cop.ContactId
where cop.MunicipalityId == 301
select c);
所以,如果重点是一次选择所有这些,我知道该怎么做,不幸的是它不是。我正在构建一个基于用户输入的查询,所以我不能一次知道所有的选择。
所以这就是我的代码:
IQueryable<Contacts> query = (from c in _ctx.Contacts select c);
//Some other logic....
/*Gets a partial name (string nameStr), and filters the contacts
so that only those with a match on names are selected*/
query = query.Where(c => c.Name.Contains(nameStr);
//Some more logic
//Gets the municipalityId and wants to filter on it! :( how to?
query = query.where(c => c.ContactOperationalPlaces ...........?);
这两种where语句的区别在于,第一种是每个联系人只有一个名字,而后者一个联系人可以包含多个操作位置...
我设法找到了一个解决方案,但这个解决方案给了我一个身份不明的对象,其中包含两个表。而且我不知道如何继续。
query.Join(_ctx.ContactOperationPlaces, c => c.Id, cop => cop.ContactId,
(c, cop) => new {c, cop}).Where(o => o.cop.municipalityId == 301);
从这个表达式返回的对象是 System.Linq.Iqueryable<{c:Contact, cop:ContactOperationalPlace}>,它不能转换为 Contacts...
所以,这就是问题所在。答案可能很简单,但我就是找不到...
最佳答案
您在 where 子句之前创建一个包含两个对象的匿名类型,并根据 ContactOperationPlaces 值对其进行过滤。之后您只需选择联系人即可。
query.Join(_ctx.ContactOperationPlaces, c => c.Id, cop => cop.ContactId,
(c, cop) => new {c, cop}).Where(o => o.cop.municipalityId == 301)
.Select(o => o.c)
.Distinct();
关于c# - 如何在 linq 连接 (lambda) 上添加 where 子句?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8531748/