EF Core中集合Any内使用Like子句无法翻译的问题
解决EF Core本地集合Like查询无法翻译的问题
直接用本地集合的Any配合EF.Functions.Like会导致EF无法将逻辑翻译为SQL,因为EF不能自动把本地集合的遍历转换为SQL中的OR拼接条件。可以通过手动构建多条件OR查询来解决:
方法1:使用PredicateBuilder动态拼接条件
如果使用LINQKit的PredicateBuilder(需要安装NuGet包LinqKit.Microsoft.EntityFrameworkCore),可以这样写:
var localStringList = new List<string>() { stringA, stringB }; var predicate = PredicateBuilder.New<YourEntityType>(); foreach (var str in localStringList) { var tempStr = str; // 避免闭包陷阱 predicate = predicate.Or(x => EF.Functions.Like(x.column, $"%{tempStr}%")); } var result = database.table.Where(predicate);
方法2:手动构建Expression表达式
如果不想引入第三方库,可以手动构建表达式树:
var localStringList = new List<string>() { stringA, stringB }; var parameter = Expression.Parameter(typeof(YourEntityType), "x"); Expression? combinedExpression = null; foreach (var str in localStringList) { // 构建 EF.Functions.Like(x.column, "%str%") 的表达式 var columnProperty = Expression.Property(parameter, nameof(YourEntityType.column)); var likePattern = Expression.Constant($"%{str}%"); var likeMethod = typeof(EF.Functions).GetMethod(nameof(EF.Functions.Like), new[] { typeof(string), typeof(string) })!; var likeExpression = Expression.Call(null, likeMethod, columnProperty, likePattern); combinedExpression = combinedExpression == null ? likeExpression : Expression.OrElse(combinedExpression, likeExpression); } var whereLambda = Expression.Lambda<Func<YourEntityType, bool>>(combinedExpression!, parameter); var result = database.table.Where(whereLambda);
原理说明
这两种方法本质都是把本地集合中的每个字符串对应的Like条件,通过OR逻辑拼接起来,最终生成的SQL类似:
SELECT * FROM table WHERE column LIKE N'%stringA%' OR column LIKE N'%stringB%'
这样EF就能正确将查询翻译为SQL,避免无法翻译的错误。
内容的提问来源于stack exchange,提问作者Akronymus
相关产品推荐
相关产品推荐

