use*_*275 2 c# linq-to-entities entity-framework
所以我正在对我的SQLServer数据库的不同方法进行一些分析.我做了vanilla TSQL,CompiledQuery和一个未编译的Linq语句.
正如预期的那样,性能按照相同的顺序进行,但是在分析后两者时我发现了一些好奇的东西.
CompiledQuery生成的SQL比普通旧语句生成的SQL要好得多.
本地SQLExpress数据库; table被称为'foreignTable',ColumnA是int,主键(索引); ColumnB是随机int.
Func<testingDatabaseEntities1, int, int> GetByPK = CompiledQuery.Compile((testingDatabaseEntities1 ft, int key)
=> (ft.foreignTable.Where(x => x.ColumnA == key).FirstOrDefault().ColumnB));
Run Code Online (Sandbox Code Playgroud)
生成
SELECT
[Project1].[ColumnB] AS [ColumnB]
FROM ( SELECT cast(1 as bit) AS X ) AS [SingleRowTable1]
LEFT OUTER JOIN (SELECT TOP (1)
[Extent1].[ColumnB] AS [ColumnB]
FROM [dbo].[foreignTable] AS [Extent1]
WHERE [Extent1].[ColumnA] = @p__linq__1 ) AS [Project1] ON 1 = 1
Run Code Online (Sandbox Code Playgroud)
对于生成的代码,这真的不是太可怕了.
但是当我做普通的Linq声明时:
entity.foreignTable.Where(x => x.ColumnA == searchForMe).FirstOrDefault().ColumnB
Run Code Online (Sandbox Code Playgroud)
它产生:
SELECT
[Limit1].[C1] AS [C1],
[Limit1].[ColumnA] AS [ColumnA],
[Limit1].[ColumnB] AS [ColumnB],
[Limit1].[FKColumn] AS [FKColumn]
FROM ( SELECT TOP (1)
[Extent1].[ColumnA] AS [ColumnA],
[Extent1].[ColumnB] AS [ColumnB],
[Extent2].[FKColumn] AS [FKColumn],
1 AS [C1]
FROM [dbo].[foreignTable] AS [Extent1]
LEFT OUTER JOIN (SELECT
[Table_2].[FKColumn] AS [FKColumn],
[Table_2].[SomeText] AS [SomeText]
FROM [dbo].[Table_2] AS [Table_2]) AS [Extent2] ON [Extent1].[ColumnA] = [Extent2].[FKColumn]
WHERE [Extent1].[ColumnA] = @p__linq__7
) AS [Limit1]
Run Code Online (Sandbox Code Playgroud)
这只是蹩脚的.
所以我想问题是:是否有可能将常规Linq给予实体与CompiledQuery相同数量的SQL suckiness?
您要比较的查询不一样.第一个编译的查询返回一个属性而不返回任何其他属性 它永远不会返回任何不同.第二个返回一个您取消引用然后访问其属性的实体实例.当查询执行时,它无法知道您只想查看一个属性.
您可以从非编译查询中获取相同SQL的一种方法(未经测试)是投影到匿名类型:
var b = (from e in entity.foreignTable.
where ColumnA == searchForMe
select new
{
ColumnB = e.ColumnB
}).FirstOrDefault().ColumnB;
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
2034 次 |
| 最近记录: |