C# 表达式到字符串

C# 表达式到字符串,c#,expression,expression-trees,C#,Expression,Expression Trees,我怎样才能得到像这样的字符串 Namespace.IMyService.Do("1") 根据本剪报中演示的表达式: IMyService myService = ...; int param1 = 1; myExpressionService.Get(c => myService.Do(param1)); 实际上,我不想调用Do,除非使用生成的字符串满足条件。您应该能够对结果表达式调用.ToString()。根据MS文档,ToString()返回表达式的文本表示形式。你试过了吗?你必

我怎样才能得到像这样的字符串

Namespace.IMyService.Do("1")
根据本剪报中演示的表达式:

IMyService myService = ...;
int param1 = 1;

myExpressionService.Get(c => myService.Do(param1));

实际上,我不想调用
Do
,除非使用生成的字符串满足条件。

您应该能够对结果表达式调用.ToString()。根据MS文档,ToString()返回表达式的文本表示形式。你试过了吗?

你必须遍历
表达式树。以下是一些示例代码:

internal static class myExpressionService
{
    public static string Get(Expression<Action> expression)
    {
        MethodCallExpression methodCallExpression = (MethodCallExpression)expression.Body;
        var method = methodCallExpression.Method;
        var argument = (ConstantExpression) methodCallExpression.Arguments.First();

        return string.Format("{0}.{1}({2})", method.DeclaringType.FullName, method.Name, argument.Value);
    }
}
内部静态类myExpressionService
{
公共静态字符串Get(表达式)
{
MethodCallExpression MethodCallExpression=(MethodCallExpression)expression.Body;
var method=methodCallExpression.method;
var argument=(ConstantExpression)methodCallExpression.Arguments.First();
返回string.Format(“{0}.{1}({2})”,method.DeclaringType.FullName,method.Name,argument.Value);
}
}
如果以这种方式调用它,它就会工作:
stringresult=myExpressionService.Get(()=>myService.Do(1))

输出为:
Namespace.IMyService.Do(1)

您可以扩展/更新它来处理您的场景。

这也可以工作(尽管它不是特别优雅):

公共静态字符串方法CallExpressionRepresentation(此LambdaExpression表达式)
{
var expression=(MethodCallExpression)expr.Body;
var arguments=string.Join(“,”,expression.arguments.OfType()。选择(x=>{
var tempInstance=((ConstantExpression)x.Expression).Value;
var fieldInfo=(fieldInfo)x.Member;
返回“\”+fieldInfo.GetValue(tempInstance.ToString()+“\”;
}).ToArray());
返回expression.Object.Type.FullName+“+expression.Method.Name+”(“+arguments+”);
}
你可以这样称呼它:

Expression<Action> expr = c => myService.Do(param1));
var repr = expr.MethodCallExpressionRepresentation();    // Namespace.IMyService.Do("1")
Expression expr=c=>myService.Do(param1));
var repr=expr.MethodCallExpressionRepresentation();//Namespace.IMyService.Do(“1”)

您的样本正确吗?你真的想要
“1”而不是
1
Namespace.IMyService.Do(“1”)
看起来像一个表达式,而不是字符串。是否要获取
“Namespace.IMyService.Do(\'1\”)
?@Snowbear是-我想要每个参数的
ToString()
结果。@Daniel:您的表达式是否总是采用
x=>foo.method(closureVariable)
?否-它应该对参数的数量灵活。它返回类似
()=>的值(Namespace.Program+c__DisplayClass0).myService.Do(1)
在本例中稍有不同的应该是argument.Value.ToString()和\“{2}”@Chris,
ToString
是不需要的。我还删除了引号,以便于阅读。无论如何,这并不完全是OP想要的,只是一个方向。@Snowbear:我如何调用该操作?@Daniel,
expression.Compile()()
将执行此任务这将在我的计算机上导致一个
InvalidCastException
——第一个参数是
MemberExpression
,而不是
ConstantExpression
Expression<Action> expr = c => myService.Do(param1));
var repr = expr.MethodCallExpressionRepresentation();    // Namespace.IMyService.Do("1")