简体   繁体   English

我应该在继承链中包含所有接口吗?

[英]Should I include all the interfaces in the inheritance chain?

If I have two interfaces: 如果我有两个接口:

    interface IGrandparent
    {
        void DoSomething();
    }

    interface IParent : IGrandparent
    {
        void DoSomethingElse();
    }

then there are two implementations: 然后有两个实现:

//only includes last interface from the inheritance chain
public class Child1 : IParent 
{
    public void DoSomething()
    {
        throw new NotImplementedException();
    }

    public void DoSomethingElse()
    {
        throw new NotImplementedException();
    }
}

// includes all the interfaces from the inheritance chain    
public class Child2 : IGrandparent, IParent     
{
    public void DoSomething()
    {
        throw new NotImplementedException();
    }

    public void DoSomethingElse()
    {
        throw new NotImplementedException();
    }
}

Are these two implementations identical? 这两个实现是否相同? (except the class name)? (班级名称除外)? Some people say there are something to do with "implicit and explicit implementation", would some one explain why? 有人说与“隐式和显式实现”有关,有人会解释为什么吗? I have seen Child2 style more than the other one. 我看到Child2风格比另一个更多。

Implicit interface implementation takes place when there is no conflicting method names from diffirent interfaces, and it is the common case. 当diffirent接口没有冲突的方法名称时会发生隐式接口实现,这是常见的情况。
Excplicit, on the other hand, is when there are conflicting method names, and at this point you have to specify which interface implements in the method. 另一方面,重复的是当存在冲突的方法名称时,此时您必须指定在该方法中实现哪个接口。

public interface IFoo
{
    void Do();   // conflicting name 1
}

public interface IBar
{
    void Do();   // conflicting name 2
}

public class FooBar : IFoo, IBar
{
    void IFoo.Do()    // explicit implementation 1
    {            
    }

    void IBar.Do()    // explicit implementation 1
    {
    }
}

Notice that excplicitly implemented interface methods cannot be public. 请注意,明确实现的接口方法不能公开。 Here you can read more about explicit interface implementation. 在这里,您可以阅读更多关于显式接口实现

Talking about your specific example. 谈谈你的具体例子。 You can safely use only IParent . 您可以安全地仅使用IParent Even if you would like to use excplicit interface implementation, you still can do it without specifically mentioning IGrandparent in class declaration. 即使你想使用激活接口实现,你仍然可以在类声明中没有特别提到IGrandparent

interface IGrandparent
{
    void DoSomething();
}

interface IParent : IGrandparent
{
    void DoSomethingElse();

    void DoSomething();
}

public class Child : IParent
{
    void IGrandparent.DoSomething()
    {
    }

    public void DoSomethingElse()
    {
    }

    public void DoSomething()
    {
    }
}

EDIT: As Dennis pointed out, there are several other cases of explicit interface implementation usage, including interface re-implementation . 编辑:正如丹尼斯所指出的,还有其他一些明确的接口实现用法,包括接口重新实现 I found very good reasoning for implicit vs explicit interface implementation usages in here (you may also want to check out the whole thread, it's fascinating). 我在这里发现了隐式vs显式接口实现用法的非常好的推理(你可能也想查看整个线程,这很有趣)。

They are identical. 它们完全相同。

This is not about explicit interface implementation, because one can implement interface explicitly using both Child1 and Child2 styles, eg: 这不是显式接口实现,因为可以同时使用显式实现接口Child1Child2风格,例如:

public class Child2 : IGrandparent, IParent
{
    void IGrandparent.DoSomething()
    {
        throw new NotImplementedException();
    }

    public void DoSomethingElse()
    {
        throw new NotImplementedException();
    }
}

public class Child1 : IParent
{
    void IGrandparent.DoSomething()
    {
        throw new NotImplementedException();
    }

    public void DoSomethingElse()
    {
        throw new NotImplementedException();
    }
}

Note, that this shouldn't be confused with interface re-implementation within class hierarchy: 注意,这不应该与类层次结构中的接口重新实现相混淆:

public class Child1 : IParent
{
    public void DoSomething()
    {
        Console.WriteLine("Child1.DoSomething");
    }

    public void DoSomethingElse()
    {
        Console.WriteLine("Child1.DoSomethingElse");
    }
}

public class Child2 : Child1, IGrandparent
{
    // Child2 re-implements IGrandparent
    // using explicit interface implementation
    void IGrandparent.DoSomething()
    {
        Console.WriteLine("Child2.DoSomething");
    }
}

I'd avoid Child2 style. 我会避免使用Child2风格。 It's just a visual trash. 这只是一个视觉垃圾。 Moreover, if IGrandparent isn't your responsibility, then sometime you will get this: 此外,如果IGrandparent不是您的责任,那么有时你会得到这个:

interface IGrandparent : ICthulhu { ... }

Do you want to update your code this way: 您想以这种方式更新您的代码:

public class Child2 : ICthulhu, IGrandparent, IParent { ... }

?

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM