如何在Java中选择接口和抽象类

什么是抽象类?

摘要意味着某些东西不是完全具体的 - 它只是一个想法或某事的要点。因此,当我们讨论抽象类时,它意味着一个本身没有具体实现的类。这只是为其他具体类创建的结构或指南。我们可以说抽象类是具体类的灵魂。这就是我们“扩展”抽象类的原因。抽象类应该只有那些属性和方法,没有它们就不能存在具体的类。

这就是Java不支持抽象类的多重继承的原因。因为一个具体的类只能表现(或占用所有属性)只有一个抽象类(显然,一个体不能有两个灵魂)。

例如,  Man 并且  Car 有许多常见的行为,例如运动,创造声音等,但是一个  Car 类只能表现得像  Vehicle一个人,而不是一个人,而且这个  Man 类只能表现得像人,而不是车辆。

我同意上面的例子是蹩脚的,但即使在现实生活场景中,如果你不确定你应该继承哪个抽象类,或者你认为需要继承多个抽象类,那么这是一种设计气味,并且你应该重新审视你的项目设计。

基于我们上面讨论的内容,我们需要创建一个  Vehicle 抽象类。这个抽象类将具有Engine,Shape等属性  Car 和相关方法。我们增加   Engine 和  Shape 在抽象类,因为可以在没有这两个不存在车辆。

抽象 类 车辆 {
  私有 String  引擎 ;
  abstract  void  startEngine();
  abstract  void  stopEngine();
}


什么是界面?

界面是不同系统之间的行为契约。在Java接口中,我们定义了一个类的行为,它将实现这个接口。一个类可以有许多不同的行为,这就是Java允许我们“实现”N个接口的原因。接口仅用于提供行为。这就是为什么Java命名约定建议使用形容词作为接口的名称。

例如,汽车可以移动,因此我们可以创建一个可移动的界面并在我们的Car班级中实现它  漂移和喇叭行为也是如此。这些是Car方法的行为  ,而不是内置属性。一  Car 会车,即使它不能移动。

interface  Movable {
  void  move();
}


令人遗憾的是,我们习惯于在几乎忘记抽象类的功能,它们的使用以及创建它们的意图的层面上使用接口。

与汽车类创建相关的虚拟Java代码

class  Car  extends  车辆 工具 Movable {

  @覆盖
  void  startEngine(){
    系统。出。println(“启动汽车引擎”);
  }

  @覆盖
  void  stopEngine(){
    系统。出。println(“停止汽车引擎”);
  }

  @覆盖
  public  void  move(){
    系统。出。println(“动车”);
  }
}


摘要

抽象类创建相关的关键要点

  • 在为具体类提供准则时创建抽象类。

  • 抽象类创建与您是否要提供任何方法的实现完全无关。

  • 仅将这些属性和行为添加到抽象类中,否则您的具体类将失去其存在。例如,  Vehicle 没有引擎就不能存在。

界面创建相关的关键要点

  • 创建为您的具体类提供附加行为的接口。当我们将这些接口共享到外部系统时,它就变成了契约,这就是为什么我们说接口是具体类的行为契约。

  • 这些行为不应该是您的课程必需的。这些行为应该为您的类添加更多功能。例如,  即使它不能移动,也Car 将是a  Car

  • 问一个问题,每当具体类实现你的界面时,它是否需要你的界面中提到的所有行为,或者只需要几个?在多个接口中重构您的接口,直到上述问题的答案为是。

谢谢阅读!


猜你喜欢

转载自blog.51cto.com/14009535/2326600
今日推荐