Why should we use interface if we can simply override methods of the superclass or use abstract classes?
我有两个程序,一个使用接口实现,另一个只使用类实现-我已经读过了,使用接口的好处是它可以提供自己的超类方法实现,但是可以使用抽象类或方法重写来实现。接口的作用是什么?在什么样的层次结构和情况下,使用接口将是最有益的?界面
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | interface Shape { void area(int x, int y); } class Rectangle implements Shape { @Override public void area(int length, int breadth) { System.out.println(length*breadth); } } class Triangle implements Shape { @Override public void area(int base, int height) { System.out.println(base*height); } } public class ShapeUsingInterface { public static void main(String X[]) { Rectangle r = new Rectangle(); Triangle t = new Triangle(); r.area(5, 4); t.area(6, 3); } } |
班
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | class Shape { void Area(int x, int y) { System.out.println(x*y); } } class Rectangle extends Shape { } class Triangle extends Shape { @Override void Area(int base, int height) { System.out.println((0.5)*base*height); } } public class CalculateArea { public static void main(String X[]) { Rectangle r = new Rectangle(); Triangle t = new Triangle(); r.Area(4, 5); t.Area(6, 8); } } |
要解释为什么要使用接口,必须首先了解继承的问题。这叫做钻石问题。简单地说,如果一个类,
我们剩下的是一个Java不喜欢的方法歧义!因此,防止这种情况的方法是确保
进入界面。这允许我们拥有多重继承的好处(将单个类作为各种不同的类型引用),并且仍然可以避免菱形问题,因为实现类提供了方法。这消除了方法的模糊性。
这意味着,例如:
1 2 3 4 5 6 7 8 9 | public abstract class MyClass { public void doSomething(); } public class MyConcreteClass extends MyClass { public void doSomething() { // do something } } |
您可以将
1 | MyClass class = new MyConcreteClass(); |
或
1 | MyConcreteClass class = new MyConcreteClass(); |
但考虑到这个实现,再也没有其他的了。你不能多上14门课,因为你可能会遇到钻石问题,但是你可以包括15门课。
1 2 |
突然间,你可以说……
1 | Seralizable myClass = new MyConcreteClass(); |
因为
简而言之:可以实现多个接口,但只能继承一个类。
我想说,在您的示例中,
如果要添加新形状,将继承实现不正确的方法。您必须记住检查所有类中的所有方法,以验证继承的方法。在接口的情况下,你不能犯这个错误。
您可以将
覆盖其他类中的所有方法(通过扩展该类并在其上实现)的
抽象类有一点不同,因为它们也实现方法(如普通类所见),而且还作为接口工作,因为它们还要求实现已声明但未实现的方法。在Java 8中,接口也可以做到这一点。
接口定义合同。比如说:
1 2 3 4 | interface MusicPlayer { public void shuffle(); } |
现在,每个实现接口的类都可以有自己的算法来实现
1 2 3 4 5 6 7 8 9 | abstract class MusicPlayer { public void turnOff() { //kill the app } abstract public void shuffle(); } |
使用接口,您可以实现多个接口,但只能扩展一个类。