Два разных оператора SQL, сгенерированных одним и тем же выражением Linq и Lambda - PullRequest
3 голосов
/ 17 ноября 2010

Это Linq для левого соединения -

var Records = from cats in Context.Categories
         join prods in Context.Products on cats.Id equals prods.Category_Id into Cps
         from results in Cps.DefaultIfEmpty()
         select new { CatName = cats.Name, ProdName = results.Name }; 

Это лямбда-выражение для того же -

var Records = Context.Categories.GroupJoin(Context.Products, c => c.Id, p => p.Category_Id, (c, p) => new { CatName = c.Name, Prods = p });     

Linq использует SQL-

SELECT 
[Extent1].[Id] AS [Id], 
[Extent1].[Name] AS [Name], 
[Extent2].[Name] AS [Name1]
FROM  [dbo].[Categories] AS [Extent1]
LEFT OUTER JOIN [dbo].[Products] AS [Extent2] ON [Extent1].[Id] = [Extent2].[Category_Id]

И лямбдаИспользует следующий SQL -

 SELECT 
 [Project1].[Id] AS [Id], 
 [Project1].[Name] AS [Name], 
 [Project1].[C1] AS [C1], 
 [Project1].[Category_Id] AS [Category_Id], 
 [Project1].[Description] AS [Description], 
 [Project1].[Id1] AS [Id1], 
 [Project1].[Name1] AS [Name1], 
 [Project1].[Price] AS [Price]
 FROM ( SELECT 
[Extent1].[Id] AS [Id], 
[Extent1].[Name] AS [Name], 
[Extent2].[Category_Id] AS [Category_Id], 
[Extent2].[Description] AS [Description], 
[Extent2].[Id] AS [Id1], 
[Extent2].[Name] AS [Name1], 
[Extent2].[Price] AS [Price], 
CASE WHEN ([Extent2].[Category_Id] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1]
FROM  [dbo].[Categories] AS [Extent1]
LEFT OUTER JOIN [dbo].[Products] AS [Extent2] ON [Extent1].[Id] = [Extent2].[Category_Id])  AS [Project1]
ORDER BY [Project1].[Id] ASC, [Project1].[C1] ASC

Мой вопрос: почему один и тот же оператор возвращает другой SQL?

Ответы [ 2 ]

2 голосов
/ 17 ноября 2010

В дополнение к ответу Джона у вас есть:

var Records = Context.Categories.GroupJoin(Context.Products, c => c.Id, p => p.Category_Id, (c, p) => new { CatName = c.Name, Prods = p });

с Prods = p (получение всей записи о продукте), где запрос Linq имеет ProdName = results.Name (получение только строки имени из сгруппированных результатов),Это значительное количество различий.

Попробуйте ввести свой Linq в LinqPad и посмотреть, как выглядит результирующая Lamba на панели результатов.

2 голосов
/ 17 ноября 2010

Это совсем не тот запрос - у вас есть GroupJoin в версии лямбда-выражения, конечно, - но у вас нет SelectMany, который бы соответствовал:

from results in Cps.DefaultIfEmpty()

Сложно определить точный перевод запроса из-за введенных прозрачных идентификаторов, но я уверен, что в этом разница.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...