why virtual is allowed while implementing the interface methods?
我有一个带有接口的特定查询。默认情况下,接口方法是抽象的和虚拟的,因此如果我们在类中实现该接口并给出定义,我们实际上会重写该方法,但是当我们在实现类中再次将该方法标记为虚拟的时候,为什么编译器没有考虑到我们实际上正试图隐藏原始的接口虚拟方法。就像在基类和派生类中有一个虚拟方法,在这种情况下,编译器会警告您正在隐藏基类方法,因此如果有意隐藏基类方法,请使用new。
1 2 3 4 5 6 7 8 9 10 11 12 | public interface ITestInterface { void virtualmethod(); // this method is by default virtual. } public class TestInterface :ITestInterface { public virtual void virtualmethod() { // Now compiler should consider that i am actually hiding the interface virtual method. } } |
如果为接口构建上述代码并在ildasm中打开,您将看到如下代码:
instance void virtualmethod() cil managed
{
}//end of method ITestInterface::virtualmethod
默认情况下,从接口实现的方法不是虚拟的。您只是提供接口定义中定义的契约的实现。通过将方法标记为
考虑这个例子:
1 2 3 4 5 6 7 8 9 10 11 12 | interface IAnimal { string Speak(); } class Dog : IAnimal { public string Speak() { return"Bark!"; } } |
现在考虑这个例子:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | interface IAnimal { string Speak(); } class Dog : IAnimal { public virtual string Speak() { return"Bark!"; } } class GoldenRetriever : Dog { public override string Speak() { return"I am a golden retriever who says" + base.Speak(); } } |
现在,
好,最后一个例子。记住,接口不需要实现——它们只需要满足契约。这意味着接口只关心具有匹配签名的实现类中是否存在成员。这意味着我们也可以这样做:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | interface IAnimal { string Speak(); } abstract class Dog : IAnimal { public abstract string Speak(); } class GoldenRetriever : Dog { public override string Speak() { return"I am a golden retriever"; } } |
注意,现在
接口也从一个类继承到另一个类,因此在上面的所有示例中,
好吧,我认为您的困惑可能来自这样一个事实:虚拟方法是在接口中定义的,而不是类。下面是我在上面定义的接口的IL:
1 2 3 4 5 6 7 | .class private interface abstract auto ansi IAnimal { .method public hidebysig newslot abstract virtual instance string Speak() cil managed { } } |
虽然您正确地将方法定义为
这里重要的是:尽管方法在接口中声明为
接口不是基类,因此实现方法不被重写。接口只声明方法,默认情况下接口方法不是虚拟的,而事实接口只声明实现该接口的类上可用的方法。
声明不能是虚拟的。
实现可以是或不能是完全依赖于实现者逻辑的虚拟实现。