为什么我的外部C#函数的参数列表中有"this"?

Sam*_*tar 2 c#

我的代码在Action方法中有以下内容:

    catch (Exception e)
    {
        log(e);
        return Content(ExceptionExtensions.GetFormattedErrorMessage(e));
    }
Run Code Online (Sandbox Code Playgroud)

调用的函数如下所示:

public static class ExceptionExtensions
{
    public static string GetFormattedErrorMessage(this Exception e)

            if (e == null)
        {
            throw new ArgumentNullException("e");
        }
Run Code Online (Sandbox Code Playgroud)

有人可以解释为什么在参数列表的开头有"this"吗?

Pen*_*hev 8

这是扩展方法的签名.它们是在.NET3.5(C#3)中引入的.没有this编译器会将其作为静态方法签名.在以下代码中:

public class Foo
{
    public void FooBar()
    {

    }
}
public static class FooEx
{
    public static void Bar(this Foo f)
    {
        f.FooBar();
    }
    public static void StaticBar(Foo f)
    {
        f.FooBar();
    }
}
Run Code Online (Sandbox Code Playgroud)

您可以像这样调用静态方法:

FooEx.StaticBar(new Foo());
Run Code Online (Sandbox Code Playgroud)

和这样的扩展方法:

new Foo().Bar();
Run Code Online (Sandbox Code Playgroud)

和扩展方法作为静态方法:

FooBar.Bar(new Foo());
Run Code Online (Sandbox Code Playgroud)

因此,要将扩展方法转换为静态方法,您只需this从签名中删除关键字即可.但是,如果要将静态方法转换为扩展方法,则必须:

  1. this关键字添加到签名中
  2. 将该方法放入非嵌套public static类中
  3. 制作方法的访问修饰符 public

Scott Hanselman有一篇关于语法选择的文章,以及它如何适应现有的CLR,只需对编译器进行最少的更改.

总之,他得出结论,在编译之后,生成的静态方法的IL代码和扩展方法的代码之间没有区别.该this关键字是否有指示编译器将周围的扩展方法的一些元数据.

我的猜测是他们已经去了this关键字,因为1.it已经存在,2.与其他现有关键字相比,它的现有意义最适合扩展方法的上下文.