是否可以为抽象类编写扩展方法

Pri*_*aka 5 c# extension-methods abstract-class

为什么我无法扩展抽象类.有没有解决这个问题的工作?

在Silverlight中,Enum.GetNames不见了.所以,我想扩展它,并在我的实用程序集中.到那时,进入了这个.

And*_*tan 6

这里的问题不在于您不能将扩展方法添加到抽象类(您可以 - 您可以向任何类型添加扩展方法) - 这是您不能将静态方法添加到具有扩展方法的类型.

扩展方法是静态方法,它们将自己作为实例方法呈现在C#中.但他们仍然是静止的.向类型添加静态方法需要能够重新定义类型,只有拥有源代码才能执行此操作:)

如果你想要这个方法,最好的办法是编写自己的静态函数,看看是否可以将代码从反射器中删除.

但是,它完全有可能不存在,因为它在Silverlight中实际上不受支持(我不知道 - 我没有调查)

编辑

继续你的评论 - 我希望我在这里了解你 - 我认为你想要做的就是这样(目标object是证明这一点):

public static class ExtraObjectStatics
{
  public static void NewStaticMethod()
  {

  }
}

public class Test
{
  public void foo()
  {
    //You can't do this - the static method doesn't reside in the type 'object'
    object.NewStaticMethod();
    //You can, of course, do this
    ExtraObjectStatics.NewStaticMethod();
  }
}
Run Code Online (Sandbox Code Playgroud)

如果你考虑一下 - 当然你不能将新的静态方法注入到现有类型中,因为就像我在第二段中所说的那样,你必须能够重新编译底层类型; 而且根本没有办法解决这个问题.

你可以做的是(我实际上并不推荐这个 - 但它是一个选项)创建一个名为的新类型Enum并将其放在一个新的命名空间中:

namespace MySystem
{
  public class Enum
  {
    public static string[] GetNames()
    {
      //don't actually know how you're going to implement it :)
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

现在 - 当你想要使用它时,你不能做的是:

using System;
using MySystem;

namespace MyCode
{
  public class TestClass
  {
    public static void Test()
    {
      Enum.GetNames(); //error: ambiguous between System and MySystem
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

因为在最外层范围内使用'System'和'MySystem'将导致编译器无法解析正确的Enum类型.

但是,你可以做的是:

using System;

namespace MyCode
{
  using MySystem; //move using to inside the namespace
  public class TestClass
  {
    public static void Test()
    {
      //will now work, and will target the 'MySystem.Enum.GetNames()'
      //method.
      Enum.GetNames();
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

现在,该命名空间内的代码(在该文件中)将始终解析Enum为命名空间中的代码,因为using就范围而言,这是最近的指令.

因此,您可以将此视为覆盖整个Enum类型,以获得包含其中的给定命名空间的好处using MySystem;.

但是,确实如此 - 它取代了现有System.EnumMySystem.Enum- 意味着你失去了所有System.Enum类型的成员.

您可以通过在Enum类型中围绕System.Enum版本编写包装器方法来解决这个问题- 确保您将类型完全限定为System.Enum.

看过Reflector中的GetNames方法的实现 - 它依赖于我认为你无法构建的内部数据......但是我很想知道你是否真的能够重现Silverlight中的方法.