在字符串上生成表达式
本文关键字:表达式 字符串 | 更新日期: 2023-09-27 18:06:33
下面的代码与StartsWith
和Contains
一起工作,但当我尝试Equals
时,我得到了这个异常:在类型'System '上有多个方法'等于'。字符串'与提供的参数兼容。
要恢复,CreatePredicate可以构建3种类型的谓词,但只有Equals
不起作用:
-
AList.Where(x => x.MyField.StartsWith("ValueToSearch")); //OK
-
AList.Where(x => x.MyField.Contains("ValueToSearch")); //OK
-
AList.Where(x => x.MyField.Equals("ValueToSearch")); //Not OK
. .
public enum TypeSearch
{
StartsWith = 1,
Contains = 2,
Equals = 3
}
private static Expression<Func<T, bool>> CreatePredicate<T>(string member, object value, TypeSearch type)
{
var p = System.Linq.Expressions.Expression.Parameter(typeof(T));
System.Linq.Expressions.Expression body = p;
foreach (var subMember in member.Split('.'))
{
body = System.Linq.Expressions.Expression.PropertyOrField(body, subMember);
}
var res = System.Linq.Expressions.Expression.Lambda<Func<T, bool>>(
System.Linq.Expressions.Expression.Call(
System.Linq.Expressions.Expression.Call(
body,
"ToUpper", null),
type.ToString(), null,
System.Linq.Expressions.Expression.Constant(value.ToString().ToUpper())
), p);
return res;
}
正如错误消息解释的那样,在string
类型(Equals(object)
和Equals(string)
)上定义了多个Equals
方法。由于您只是使用名称来定位您想要的方法,因此匹配是不明确的。
一个解决方案是将方法的MethodInfo
传递给Expression.Call
,例如
MethodInfo equalsMethod = typeof(string).GetMethod("Equals", new[] { typeof(string) });
Expression.Call(instanceExpr, equalsMethod, Expression.Constant(value.ToString().ToUpper()));