Linq To Sql左外连接 - 过滤null结果

时间:2010-03-28 05:28:53

标签: c# linq-to-sql inner-join

我想将以下SQL重现为C#LinqToSql

SELECT TOP(10) Keywords.*
FROM         Keywords 
LEFT OUTER JOIN IgnoreWords 
  ON Keywords.WordID = IgnoreWords.ID
WHERE  (DomainID = 16673) 
  AND (IgnoreWords.Name IS NULL)
ORDER BY [Score] DESC

以下C#Linq给出了正确的答案 但我不禁想到我错过了一些东西(更好的方法吗?)

var query = (from keyword in context.Keywords
     join ignore in context.IgnoreWords 
        on keyword.WordID equals ignore.ID into ignored
     from i in ignored.DefaultIfEmpty()
     where i == null
     where keyword.DomainID == ID
     orderby keyword.Score descending
     select keyword).Take(10);

生成的SQL看起来像这样:

SELECT TOP (10) 
       [t0].[DomainID]
     , [t0].[WordID]
     , [t0].[Score]
     , [t0].[Count]
  FROM [dbo].[Keywords] AS [t0]
  LEFT OUTER JOIN 
    (  SELECT 1 AS [test]
            , [t1].[ID] 
         FROM [dbo].[IgnoreWords] AS [t1]
    ) AS [t2] 
    ON [t0].[WordID] = [t2].[ID] 
WHERE ([t0].[DomainID] = 16673) 
  AND ([t2].[test] IS NULL)
ORDER BY [t0].[Score] DESC

如何摆脱这种冗余的内在选择? 它只是略贵一点,但每一点都有帮助!

1 个答案:

答案 0 :(得分:4)

我认为你可以做这样的事情来消除左连接并可能提高效率:

var query = (from keyword in context.Keywords
             where keyword.DomainID == ID 
             && !(from i in context.IgnoreWords select i.ID).Contains(keyword.WordID)
             orderby keyword.Score descending
             select keyword)
            .Take(10);