为什么没有捕获的 lambda 从 C# 5 中的静态更改为 C# 6 中的实例方法? [英] Why has a lambda with no capture changed from a static in C# 5 to an instance method in C# 6?

查看:11
本文介绍了为什么没有捕获的 lambda 从 C# 5 中的静态更改为 C# 6 中的实例方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

此代码在标记的行上抛出异常:

This code throws an exception on the marked line:

using System;
using System.Linq.Expressions;

namespace ConsoleApplication2
{
    class Program
    {
        static void Main(string[] args)
        {
            Action<int, int> a = (x, y) => Console.WriteLine(x + y);

            ParameterExpression p1 = Expression.Parameter(typeof(int), "p1");
            ParameterExpression p2 = Expression.Parameter(typeof(int), "p2");

            // Here is the exception ArgumentNullException.
            MethodCallExpression call = Expression.Call(a.Method, p1, p2);
        }
    }
}

现在,我已经在 VS2013(就像一个魅力)和 VS2015 社区(抛出异常)中测试了这段代码.

Now, I've tested this code in VS2013 (works like a charm) and in VS2015 Community (throws the exception).

我遵循了 .Net 参考源,这导致一些代码条件检查提供的方法是否IsStatic.

I followed the .Net Reference Source, which led me to some code condition which checkes whether the supplied method IsStatic or not.

就我而言,我传递的方法 (a.Method) 在 VS2013 中是静态的,出于某种原因,在 VS2015 中是 非静态(实例).如果没有,它会抛出,告诉我我没有提供 Instance 参数.

In my case, the method I pass (a.Method) is static in VS2013 and for some reason non static (instance) in VS2015. If not, it throws, telling me that I did not supply the Instance argument.

为什么会这样?如何避免这种情况,以便 Expression.Call 在新的 Visual Studio 中重新开始工作?

Why is it so? How can this be avoided so that Expression.Call would begin to work again in new Visual Studio?

推荐答案

我不知道为什么会这样(也在本地复制).

I don't have an answer as to why that is so (reproduced locally, too).

然而,答案是:

为什么会这样?如何避免这种情况,以便 Expression.Call重新开始在新的 Visual Studio 中工作?

Why is it so? How can this be avoided so that Expression.Call would begin to work again in new Visual Studio?

您可以这样做(适用于两种编译器):

You can do this (works on both compilers):

Action<int, int> a = (x, y) => Console.WriteLine(x + y);

ParameterExpression p1 = Expression.Parameter(typeof(int), "p1");
ParameterExpression p2 = Expression.Parameter(typeof(int), "p2");

MethodCallExpression call;
if (a.Method.IsStatic)
{
    call = Expression.Call(a.Method, p1, p2);
}
else
{
    call = Expression.Call(Expression.Constant(a.Target), a.Method, p1, p2);
}

感谢 Jeppe Stig Nielsen 修复了 a.Target

这篇关于为什么没有捕获的 lambda 从 C# 5 中的静态更改为 C# 6 中的实例方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆