我做了以下查询:
var list = from book in books
where book.price > 50
select book;
list = list.Take(50);
我希望上面的内容能够生成:
SELECT top 50 id, title, price, author
FROM Books
WHERE price > 50
但它会产生:
SELECT
[Limit1].[C1] as [C1]
[Limit1].[id] as [Id],
[Limit1].[title] as [title],
[Limit1].[price] as [price],
[Limit1].[author]
FROM (SELECT TOP (50)
[Extent1].[id] as as [Id],
[Extent1].[title] as [title],
[Extent1].[price] as [price],
[Extent1].[author] as [author]
FROM Books as [Extent1]
WHERE [Extent1].[price] > 50
) AS [Limit1]
为什么上面的linq查询会生成子查询以及C1来自哪里?
答案 0 :(得分:2)
免责声明:我以前从未使用过LINQ ......
我的猜测是分页支持?我想你有某种Take(50, 50)
方法可以获得50条记录,从记录50开始。看看查询生成的SQL,你可能会发现它使用类似的子查询结构来允许它返回查询中的任何50行,大约是它返回前50行的时间量。
在任何情况下,嵌套的子查询都不会增加任何性能开销,因为它在编译执行计划期间会自动优化。
答案 1 :(得分:1)
你仍然可以像这样清洁:
var c = (from co in db.countries
where co.regionID == 5
select co).Take(50);
这将导致:
Table(country).Where(co => (co.regionID = Convert(5))).Take(50)
相当于:
SELECT TOP (50) [t0].[countryID], [t0].[regionID], [t0].[countryName], [t0].[code]
FROM [dbo].[countries] AS [t0]
WHERE [t0].[regionID] = 5
编辑:评论,它不一定是因为单独的Take(),你仍然可以这样使用它:
var c = (from co in db.countries
where co.regionID == 5
select co);
var l = c.Take(50).ToList();
结果与以前相同。
SELECT TOP (50) [t0].[countryID], [t0].[regionID], [t0].[countryName], [t0].[code]
FROM [dbo].[countries] AS [t0]
WHERE [t0].[regionID] = @p0
你写IQueryable = IQueryable.Take(50)
的事实在这里很棘手。
答案 2 :(得分:0)
子查询是为了投影目的而生成的,当您从多个表中选择一个匿名对象时更有意义,然后外部查询用于收集结果。
尝试使用类似的内容:
from book in books
where price > 50
select new
{
Title = book.title,
Chapters = from chapter in book.Chapters
select chapter.Title
}
答案 3 :(得分:0)
是不是第一个查询返回总行数而第二个是根据对.Take()方法的调用提取行子集的情况?
答案 4 :(得分:0)