简体   繁体   English

抽象类或接口。 哪种方式是正确的?

[英]Abstract class or interface. Which way is correct?

There are two way for choosing between abstract class or interface. 在抽象类或接口之间进行选择有两种方法。 Microsoft solution and Oracle solution: Microsoft解决方案和Oracle解决方案:


Microsoft, design guideline: 微软,设计指南:

Do use abstract (MustInherit in Visual Basic) classes instead of interfaces to decouple the contract from implementations. 使用抽象(Visual Basic中的MustInherit)类而不是接口来将合同与实现分离。

http://msdn.microsoft.com/en-us/library/ms229013.aspx http://msdn.microsoft.com/en-us/library/ms229013.aspx


Oracle, The Java Tutorials: Oracle,Java教程:

If an abstract class contains only abstract method declarations, it should be declared as an interface instead. 如果抽象类只包含抽象方法声明,则应将其声明为接口。

http://docs.oracle.com/javase/tutorial/java/IandI/abstract.html http://docs.oracle.com/javase/tutorial/java/IandI/abstract.html


My question is which way is correct? 我的问题是哪种方式是正确的? Microsoft or Oracle solution? Microsoft或Oracle解决方案? Note that I think choose between abstract class or interface should not depends on programming language (Java or C#). 请注意,我认为抽象类或接口之间的选择不应该依赖于编程语言(Java或C#)。

If I recall my blog reading correctly, the Microsoft advice to use abstract classes stems from the ability to reuse implementation with an abstract class, something you can't do with an interface. 如果我回想起我的博客正确阅读,微软使用抽象类的建议源于使用抽象类重用实现的能力,这是接口无法做到的。

Note also that the Microsoft page you linked to is specifically guidance for writing code libraries for sharing/reuse across multiple projects. 另请注意,您链接到的Microsoft页面是编写代码库以跨多个项目共享/重用的专门指导。 The likelihood in this situation is that you'll be writing all the implementations of the interface yourself, probably within the same assembly. 在这种情况下的可能性是您将自己编写接口的所有实现,可能在同一个程序集中。 Good practices for working on a single product or system will vary somewhat. 在单个产品或系统上工作的良好实践会有所不同。

One common approach that I've seen across a number of codebases in a number of languages is this: 我在许多语言的许多代码库中看到的一种常见方法是:

  • Define an interface to specify the contract 定义用于指定合同的接口
  • Create an abstract class implementing the contract to provide any common implementation useful to all descendants 创建一个实现契约的抽象类,以提供对所有后代有用的任何常见实现
  • Implementations of the contract then have the option to start from the base class for convenience, or just to implement the interface if they want full control 然后,合同的实现可以选择从基类开始以方便使用,或者只是在需要完全控制时实现接口

A fourth step common in the .NET world is to provide convenience extension functions built on the interface. .NET世界中常见的第四步是提供基于接口构建的便利扩展功能。

They are 2 statements for different contexts. 对于不同的上下文,它们是2个语句。

The Microsoft guideline you quote from is for "Designing Class Libraries". 您引用的Microsoft指南适用于“设计类库”。 And it states the reason for favoring abstract classes there: you can add functionality without breaking anything. 它说明了在那里支持抽象类的原因:你可以添加功能而不会破坏任何东西。

For separation and decoupling over layers and other boundaries, Microsoft also advices interfaces. 对于层和其他边界的分离和解耦,Microsoft也建议接口。

An interface carries no implementation - it's a contract. 接口没有实现 - 这是一个合同。 It allows for complete decoupling. 它允许完全去耦。

I will go from an interface to an abstract (base) class if I want to provide some common implementation while forcing on the inheriting class concrete class to provide some implementation specific to that class. 如果我想提供一些常见的实现,同时强制继承类具体类来提供特定于该类的一些实现,我将从接口转到抽象(基类)类。 That's provides a little less decoupling. 这提供了一点点脱钩。

Also be aware that many languages like C# (and .net languages like VB.net etc...) as well as Java do not allow multiple inheritance so interfaces become a way of allowing a class to have many behaviors. 还要注意许多语言,如C#(和.net等语言,如VB.net等)以及Java都不允许多重继承,因此接口成为允许类具有许多行为的一种方式。

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

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