2011-10-14 79 views
13

有许多关于LINQ和多个连接的文章。 但是,我没有找到任何解决方案,我想要做的连接。LINQ to Entity:多个连接条件

的SQL相当于将是这样的:

SELECT * FROM table1 a 
LEFT JOIN table2 b ON a.col1 = b.key1 AND 
a.col2 = b.key2 AND 
b.from_date <= now() AND 
b.deleted = 0; 

下面是我尝试

var query = (from x in context.table1 
      join y in context.table2 on new {x.col1, x.col2} equals {b.key1, b.key2} 
      into result 
      from result...... 

我如何可以添加日期的产生额外的条件,并删除了大量的LINQ查询之一旗? 如果我使用.Where条件,那么这被视为内连接,而不是左连接。

回答

32

另一种方式也能像

var query = (from x in context.table1 
      join y in context.table2 on 
      new { 
        Key1 = x.col1, 
        Key2 = x.col2 
        Key3 = true, 
        Key4 = true 
       } 
      equals 
      new { 
        Key1 = y.key1, 
        Key2 = y.key2, 
        Key3 = y.from_date< DateTime.Now, 
        Key4 = !y.deleted 
       } 
      into result 
from r in result.DefaultIfEmpty() 
select new {x.Something, r.Something} 
1

你不只是用第二个查询过滤第一个结果集吗?

var query = (from x in context.table1 
      join y in context.table2 on new {x.col1, x.col2} equals {b.key1, b.key2} 
      into result 
query = from x in query 
     where ... 

会这样吗?

11

LINQ支持联接语法和旧的ANSI-82 WHERE语法。使用后面的,你可以做你想要的东西

var nowTime = DateTime.Now; 
var query = from a in context.table1 
      from b in context.table2 
      where a.col1 == b.key1 
       && a.col2 == b.key2 
       && b.from_date < nowTime 
       && b.deleted == false 
      select ???; 

或者,你可以使用where和join的混合。 (要知道,在LINQ查询的顺序并不需要模仿你在SQL做什么以及订单更灵活。)

var nowTime = DateTime.Now; 
var query = from b in context.table2 
      where b.from_date < nowTime 
       && b.deleted == false 
      join a on new {b.key1, b.key2} equals new {a.col1, a.col2} 
      select ???; 
0

我有问题,在匿名的对象属性的命名:

var subscriptions = context.EmailSubscription.Join(context.EmailQueue, 
        es => new { es.Id, 9 }, 
        eq => new { eq.EmailSubscriptionId, eq.EmailTemplateId }, 
        (es, eq) => new { es.Id, eq.Id } 
       ).ToList(); 

编译器不高兴所以上面的答案帮助我弄清楚什么是错的,这里是我的工作解决方案。我花了一段时间才找到愚蠢的错误:):

var subscriptions = context.EmailSubscription.Join(context.EmailQueue, 
        es => new { EmailSubscriptionId = es.Id, EmailTemplateId = 9 }, 
        eq => new { eq.EmailSubscriptionId, eq.EmailTemplateId }, 
        (es, eq) => new { es.Id, eq.Id } 
       ).ToList();