C# 如何向linq二进制表达式添加特定于类型的实现?
我有一个相当简单的表达式解析器,它使用Linq.expression名称空间 输入类似于:(1+1),它查找左常量和右常量,并将运算符char转换为ExpressionTypes枚举值,创建适当的表达式,编译并执行 我真的希望能够进行字符串操作,(C# 如何向linq二进制表达式添加特定于类型的实现?,c#,linq,lambda,C#,Linq,Lambda,我有一个相当简单的表达式解析器,它使用Linq.expression名称空间 输入类似于:(1+1),它查找左常量和右常量,并将运算符char转换为ExpressionTypes枚举值,创建适当的表达式,编译并执行 我真的希望能够进行字符串操作,(abc+def)将计算为abcdef,但是: System.InvalidOperationException:未为类型“System.String”和“System.String”定义二进制运算符Add 我将如何着手实施这一点呢 类似于表达式Type
abc
+def
)将计算为abcdef
,但是:
System.InvalidOperationException:未为类型“System.String”和“System.String”定义二进制运算符Add
我将如何着手实施这一点呢
类似于表达式Types.Concat的EqualLant的东西是理想的。您必须自己创建MethodCallExpression,在本例中,它是用于静态方法string.Concat的。(这是编译器在编译此类代码时自己所做的)您必须自己创建MethodCallExpression,在本例中,它用于静态方法string.Concat。(这是编译器在编译此类代码时自己所做的)对于自定义运算符,它实际上是一个方法调用,因此您需要找到相应的方法并创建用于调用该方法的表达式树。没有太多的表达式树的工作,所以我很抱歉,我不能给你一个代码示例,但我希望这对自定义操作符仍然有帮助,它实际上是一个方法调用,所以你需要找到相应的方法并创建表达式树来调用该方法。我对表达式树没有太多的了解,所以我很抱歉我不能给你一个代码示例,但我希望这对你仍然有帮助。下面是一些代码,演示如何使用MethodInfo扩展二进制表达式的定义,并将其添加到字符串的串联中 一个示例使用字符串类型中现有的Concat方法 第二个示例在程序类型中使用了一个自定义Concat方法(该方法都嵌入在该类中):
下面的一些代码演示了如何使用MethodInfo扩展二进制表达式的定义,并将其添加到字符串的串联中 一个示例使用字符串类型中现有的Concat方法 第二个示例在程序类型中使用了一个自定义Concat方法(该方法都嵌入在该类中):
private MethodInfo ConcatMethod = typeof(string).GetMethod("Concat", new Type[] { typeof(string), typeof(string) });
private MethodInfo ConcatMethod2 = typeof(Program).GetMethod("Concat", new Type[] { typeof(string), typeof(int) });
public static string Concat(string obj1, int obj2)
{
return string.Concat(obj1, obj2.ToString());
}
private Expression SomeCode(string leftStr, string rightStr)
{
Expression left = Expression.Constant(leftStr);
Expression right = Expression.Constant(rightStr);
return Expression.Add(left, right, ConcatMethod);
}
private Expression SomeCode(string leftStr, int rightInt)
{
Expression left = Expression.Constant(leftStr);
Expression right = Expression.Constant(rightInt);
return Expression.Add(left, right, ConcatMethod2);
}
static void CheesyTest2()
{
Program foo = new Program();
Expression exp = foo.SomeCode("abc", "def");
LambdaExpression lambdaExpression = Expression.Lambda(exp);
Delegate func = lambdaExpression.Compile();
object result = func.DynamicInvoke();
Console.WriteLine(string.Format("Expression result: {0}", result));
exp = foo.SomeCode("abc", 42);
lambdaExpression = Expression.Lambda(exp);
func = lambdaExpression.Compile();
result = func.DynamicInvoke();
Console.WriteLine(string.Format("Expression2 result: {0}", result));
}