静态方法无法实现接口方法,为什么?

时间:2010-10-18 08:05:10

标签: c#

interface IXXX
{
    void Foo();
}

class XXX : IXXX
{
    public static void Foo()
    {
        Console.WriteLine("From XXX");
    }
}


class Program 
{
    static void Main(string[] args)
    {
        XXX.Foo();

    }
}

编译器错误:XXX.Foo()无法实现接口成员,因为它是静态的。

为什么静态方法不能实现接口方法?

6 个答案:

答案 0 :(得分:11)

请参阅JoelOnSoftware中描述其背后原因的帖子。

基本上,接口是使用者和提供者之间的契约,静态方法属于类,而不是类的每个实例。

关于SO的早期问题也涉及完全相同的问题: Why Doesn't C# Allow Static Methods to Implement an Interface?

答案 1 :(得分:4)

接口定义对象必须响应的行为。 由于Foo是静态方法,因此对象不响应它。换句话说,你不能写......

XXX myXXX = new XXX();
myXXX.Foo();

换句话说,myXXX并不完全满足界面的要求。

答案 2 :(得分:2)

如果我们将接口视为对象可以执行接口中列出的方法的承诺,那么静态实现的想法就会成为问题。如果实现是静态的,那么就不能编写新的ImplementingObject()。ImplementedMthod。该对象无法执行该方法,该类可以。

答案 3 :(得分:2)

您使用接口来避免在实例化期间使用具体类。您无法通过实例化类访问静态方法,因此不允许使用静态方法实现接口方法。

答案 4 :(得分:1)

嗯,我相信在泛型类型参数的情况下应该允许它。它可能简化了合同单身人士课程。这是一个例子:

public interface IEntity {
   // some constrains...
  DataRow ObjToRow(object obj);
  object RowToObj(DataRow dr);
}

//T would be any class inherites from IEntity with default contructor signature.
public interface IMyContract {
  T read<T>() where T : IEntity;  
  void write<T>(T object) where T : IEntity;
}

//everything in the class is static
public static class SqlProvider : IMyContract {

  public static T read<T>() where T: IEntity {
    DataRow dr = [reading from database]
    return T.RowToObj(dr);
  }

  //compile error here....
  public static void write<T>(T obj) where T : IEntity {
    DataRow dr = T.ObjToRow(obj);

   [ ... commit data row dr to database ... ]

  }
}

public static class MyAppleEntity : IEntity  {
  [... implement IEntity contract normally ... ]
}

public static class MyOrangeEntity : IEntity {
   [... implement IEntity contract normally ... ]
}

public class MyTest {
  void reading() {
     MyAppleEntity apple = SqlProvider.Read<MyAppleEntity>();
     MyOrangeEntity orange = SqlProvider.Read<MyOrangeEntity>();

     SqlProvider.write<MyAppleEntity>(apple); 
     SqlProvider.write<MyOrangeEntity>(orange);
  } 

}

唯一一次类型引用隐含在SqlProvider.read()中,而write()和T在调用时是良好的标识。如果没有接口的静态实现,我就不得不这样写。

public class MyAppleEntity : IEntity  {
  [... implement IEntity contract normally ... ]
}

  .....

  public T read<T>() where T: IEntity, new() {
    DataRow dr = [reading from database]
    return new T().RowToObj(dr);
  }

差别很小但不太优雅。

答案 5 :(得分:0)

因为接口成员是公共的并且可以覆盖,并且静态方法不能被设计覆盖或抽象,所以接口在这里定义一个必须通过其具体实现实现的可访问契约(具有抽象实现和继承的许多步骤)之间的接口)据我所知,没有办法创建一个抽象的静态方法。