简体   繁体   English

实体框架 - Linq NOT IN查询

[英]Entity Framework - Linq NOT IN query

I've seen several other posts asking similar question but frankly I'm confused. 我已经看到其他几个帖子提出类似问题,但坦率地说我很困惑。 I'm trying to do the following sql statement in EntityFarmework and Linq but cant get the 'NOT IN' and 'UNION' working 我正在尝试在EntityFarmework和Linq中执行以下sql语句,但是无法使'NOT IN'和'UNION'正常工作

SELECT LmsTeam.* FROM LmsTeam
INNER JOIN Game ON LmsTeam.GameId = Game.ID 
WHERE LmsTeam.Id NOT IN 
(SELECT TeamHomeId as TeamID FROM LmsEventMatch WHERE EventId =1
UNION
SELECT TeamAwayId as TeamID FROM LmsEventMatch WHERE EventId =1)
AND LmsTeam.GameId = 1 AND LmsTeam.Active = 1

So I've got the join and some of the where clause as below but can't do the NOT IN and UNION clauses. 所以我得到了join和一些where子句,如下所示,但不能执行NOT INUNION子句。

from t in LmsTeams
join g in Games on t.GameId equals g.Id
  where t.GameId == 1 && t.Active == true
  select t

How about that: 那个怎么样:

from t in LmsTeams
join g in Games on t.GameId equals g.Id
where t.GameId == 1 && t.Active == true && !(
        (from m in LmsEventMatch where m.EventId == 1 select m.TeamHomeId).Union(
         from m in LmsEventMatch where m.EventId == 1 select m.TeamAwayId)
    ).Contains(t.Id)
select t

I haven't tested it because don't have your data context, but think it should be done that way. 我没有测试它,因为没有你的数据上下文,但认为应该这样做。

Update 更新

I think you can avoid Union here: 我想你可以在这里避免Union

from t in LmsTeams
join g in Games on t.GameId equals g.Id
where t.GameId == 1 && t.Active == true && !(
        LmsEventMatch.Where(m => m.EventId == 1).SelectMany(m => new int[] { m.TeamHomeId, TeamAwayId })
    ).Contains(t.Id)
select t

Another solution is to use Left outer join and keep the records where joined columns are null. 另一种解决方案是使用Left outer join并保留连接列为null的记录。

An example is given below: 下面给出一个例子:

var query = db.Categories    
  .GroupJoin(db.Products,
      Category => Category.CategoryId,
      Product => Product.CategoryId,
      (x, y) => new { Category = x, Products = y })
  .SelectMany(
      xy => xy.Products.DefaultIfEmpty(),
      (x, y) => new { Category = x.Category, Product = y })
  .Where(w => w.Product.CategoryId == null)
  .Select(s => new { Category = s.Category});

you can write and divide you query as below that will resolve your issue easily. 您可以按如下方式编写和划分查询,以便轻松解决您的问题。

Also check my post : SQL to LINQ ( Case 7 - Filter data by using IN and NOT IN clause) 另请检查我的帖子: SQL到LINQ(案例7 - 使用IN和NOT IN子句过滤数据)

//first do the union of two
var query = ((from d in  LmsEventMatch 
             where d.EventId == 1
              select d.TeamHomeId).
        Union(from e in  LmsEventMatch 
                       where e.EventId == 1
                          select e.TeamAwayId));

//than perform !contains operation for no in
var records =( from t in LmsTeams
join g in Games on t.GameId equals g.Id
  where t.GameId == 1 && t.Active == true && !query.Contains(t.Id)
  select t).ToList();

graphical representation of in and not in - linq query in和linq查询的图形表示

在此输入图像描述


for conversion from sql to linq you can use : Linqer 从sql转换为linq你可以使用: Linqer 在此输入图像描述

var homeIds = LmsEventMatch.Where(em => em.Eventid == 1)
                           .Select(em => em.TeamHomeId);
var awayIds = LmsEventMatch.Where(em => em.Eventid == 1)
                           .Select(em => em.TeamAwayId);
var allIds = homeIds.Union(awayIds);

var query = LmsTeams.Where( 
                t => !allIds.Contains( t.Id ) && t.Active == 1 && t.GameId == 1);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM