繁体   English   中英

C#中表达式树的ByRef参数

[英]ByRef parameters with Expression trees in C#

如果我想创建一个表达式树,该表达式调用带有out参数的方法,然后返回out值作为结果..我将如何处理它?

以下不起作用(抛出运行时异常),但也许最能说明我正在尝试做的事情:

private delegate void MyDelegate(out int value);
private static Func<int> Wrap(MyDelegate dele)
{
    MethodInfo fn = dele.Method;
    ParameterExpression result = ParameterExpression.Variable(typeof(int));
    BlockExpression block = BlockExpression.Block(
        typeof(int), // block result
        Expression.Call(fn, result), // hopefully result is coerced to a reference
        result); // return the variable
    return Expression.Lambda<Func<int>>(block).Compile();
}

private static void TestFunction(out int value)
{
    value = 1;
}

private static void Test()
{
    Debug.Assert(Wrap(TestFunction)() == 1);
}

我知道这可以在原始IL(或者根本没有运行时编译)中相当容易地解决,但不幸的是,这是一个更大的表达式构建过程的一部分...所以我真的希望这不是一个限制,因为完全重写将不仅仅是一种痛苦。

这对我有用:

    private static Func<int> Wrap(MyDelegate dele)
    {
        var fn = dele.Method;
        var result = ParameterExpression.Variable(typeof(int));
        var block = BlockExpression.Block(
            typeof(int),
            new[] { result },
            new Expression[]
            {
                Expression.Call(fn, result),
                result,
            });
        return Expression.Lambda<Func<int>>(block).Compile();
    }

也许这只是我,但我并没有真正看到整个事情的重点。 要完成你想要做的事情,你真的不需要写所有的东西。

控制台应用中的示例代码:

    class Program
    {
        static void Main(string[] args)
        {
            var temp = Execute(DoSomething);
            Console.Write(temp);
            Console.Read();
        }

        static int Execute(Func<int> methodToRun)
        {
            return methodToRun.Invoke();
        }

        static int DoSomething()
        {
            return 1;
        }
    }

如您所见,它以更简洁和清晰的方式为您提供相同的结果。 我认为你错过的是ActionAction<>Func<>都是delegate sintactic糖所以不需要混合2种语法而不需要像你正在做的那样重建整个表达式。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM