Entity Framework 和扩展方法中的委托
Entity Framework and delegates in extension methods
最近我在使用 EF 的 LINQ 扩展中使用委托作为谓词时遇到了问题。
这是一个简单的例子。
Func<LmsIdentityUser, bool> predicate = u => u.FullName.Contains(val) || u.EmployeeId.Contains(val);
var result = _ctx.Users.Where(predicate).ToList();
var result2 = _ctx.Users.Where(u => u.FullName.Contains(val) || u.EmployeeId.Contains(val)).ToList();
我预计这两个查询应该产生相同的 SQL 查询,因为 Where()
中使用的谓词是相同的。唯一的区别是,在第一种情况下,它是使用委托定义的。
但这里是 EF 针对这些情况生成的实际 SQL 查询。
案例一(使用委托)
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[EmployeeId] AS [EmployeeId],
[Extent1].[FullName] AS [FullName]
FROM [dbo].[AspNetUsers] AS [Extent1]
案例二(直接使用lambda)
SELECT TOP (15)
[Extent1].[Id] AS [Id],
[Extent1].[EmployeeId] AS [EmployeeId],
[Extent1].[FullName] AS [FullName]
FROM [dbo].[AspNetUsers] AS [Extent1]
WHERE ([Extent1].[FullName] LIKE @p__linq__0 ESCAPE N'~') OR ([Extent1].[EmployeeId] LIKE @p__linq__1 ESCAPE N'~')
所以问题是委托有什么问题?我应该怎么做才能在 LINQ 扩展中使用它们?
委托的形式为 Func<Input, Output>
,而 LINQ 查询的形式为 Expression<Func<Input, Output>>
。 LINQ 解析表达式以生成查询,而委托对 SELECT 查询返回的数据进行操作。请注意,委托版本根本没有过滤。
我相信您可以将谓词更改为 Expression<Func<>>
以获得您正在寻找的行为。
最近我在使用 EF 的 LINQ 扩展中使用委托作为谓词时遇到了问题。 这是一个简单的例子。
Func<LmsIdentityUser, bool> predicate = u => u.FullName.Contains(val) || u.EmployeeId.Contains(val);
var result = _ctx.Users.Where(predicate).ToList();
var result2 = _ctx.Users.Where(u => u.FullName.Contains(val) || u.EmployeeId.Contains(val)).ToList();
我预计这两个查询应该产生相同的 SQL 查询,因为 Where()
中使用的谓词是相同的。唯一的区别是,在第一种情况下,它是使用委托定义的。
但这里是 EF 针对这些情况生成的实际 SQL 查询。
案例一(使用委托)
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[EmployeeId] AS [EmployeeId],
[Extent1].[FullName] AS [FullName]
FROM [dbo].[AspNetUsers] AS [Extent1]
案例二(直接使用lambda)
SELECT TOP (15)
[Extent1].[Id] AS [Id],
[Extent1].[EmployeeId] AS [EmployeeId],
[Extent1].[FullName] AS [FullName]
FROM [dbo].[AspNetUsers] AS [Extent1]
WHERE ([Extent1].[FullName] LIKE @p__linq__0 ESCAPE N'~') OR ([Extent1].[EmployeeId] LIKE @p__linq__1 ESCAPE N'~')
所以问题是委托有什么问题?我应该怎么做才能在 LINQ 扩展中使用它们?
委托的形式为 Func<Input, Output>
,而 LINQ 查询的形式为 Expression<Func<Input, Output>>
。 LINQ 解析表达式以生成查询,而委托对 SELECT 查询返回的数据进行操作。请注意,委托版本根本没有过滤。
我相信您可以将谓词更改为 Expression<Func<>>
以获得您正在寻找的行为。