Java-将类抽象为普通类 公共抽象类图形 { 私有整数偏移; 公众人物() { 偏移量=0; } 公众人物(内部补偿) { 偏移量=偏移量; } 公共void setOffset(int newOffset) { 偏移量=新偏移量; } 公共int getOffset() { 返回偏移量; } 公共抽象空(此处为空); /** *在图形的线号线处绘制图形 *当前行。 */ 公共作废图纸(内部线号) { 整数计数; 对于(计数=0;计数时不做任何事情)将是不有用的(特别是,如果您认为这样的对象是错误的),那么您应该保持类的抽象性。即使您可以为每个方法定义一个实现,这种推理也适用。

Java-将类抽象为普通类 公共抽象类图形 { 私有整数偏移; 公众人物() { 偏移量=0; } 公众人物(内部补偿) { 偏移量=偏移量; } 公共void setOffset(int newOffset) { 偏移量=新偏移量; } 公共int getOffset() { 返回偏移量; } 公共抽象空(此处为空); /** *在图形的线号线处绘制图形 *当前行。 */ 公共作废图纸(内部线号) { 整数计数; 对于(计数=0;计数时不做任何事情)将是不有用的(特别是,如果您认为这样的对象是错误的),那么您应该保持类的抽象性。即使您可以为每个方法定义一个实现,这种推理也适用。,java,class,abstract,Java,Class,Abstract,在这个类中,它处理用于创建树的图形。我试图通过简单地给抽象方法一个主体,把它变成一个普通类。我注意到,当我删除抽象标记时,它仍然可以正常工作。但我的问题是,如果我想让这个类非抽象化,我将通过什么方式来实现这一点 这个类被另外两个类扩展,然后它就有了主类。我是否也必须检查并修改它们?如果你想要一个非抽象类,那么你不能用抽象修饰符声明它(即只公共类图)。不需要修改任何派生类(只要它们本身不是抽象的)。您不应该修改图;你应该扩展它 这个类由另外两个类扩展 类,然后它有主 班级。我必须通过和 也要修改吗

在这个类中,它处理用于创建树的图形。我试图通过简单地给抽象方法一个主体,把它变成一个普通类。我注意到,当我删除抽象标记时,它仍然可以正常工作。但我的问题是,如果我想让这个类非抽象化,我将通过什么方式来实现这一点


这个类被另外两个类扩展,然后它就有了主类。我是否也必须检查并修改它们?

如果你想要一个非抽象类,那么你不能用
抽象
修饰符声明它(即只
公共类图
)。不需要修改任何派生类(只要它们本身不是抽象的)。

您不应该修改图;你应该扩展它

这个类由另外两个类扩展 类,然后它有主 班级。我必须通过和 也要修改吗

更重要的是,不要修改图:您将破坏代码的其余部分


您不应该修改任何内容。创建一个扩展Figure的新类,并用所需的行为重写abstract drawHere()方法。

从技术上讲,要使抽象类非抽象,必须:

  • 提供所有抽象方法的实现
  • 因为您现在拥有了定义的所有内容的有效实现,所以请删除所有抽象标记
不需要修改继承类中的任何内容(假设它们是非抽象类本身),因为它们已经提供了父类的所有抽象方法的实现&可以自由重写它们想要的任何方法


您是否应该使类成为非抽象类是另一个讨论点。

删除
abstract
关键字并实现抽象方法使类成为非抽象类是正确的

但是,您通常不希望将类本身从抽象转换为非抽象。在添加此关键字之前,类不是抽象的,因此您(或其他人)显然有理由确保它不是普通类,而是抽象类

如果您从非常高的层次(远离Java)来考虑它,那么“树”就是您知道如何绘制的东西。类似地,您可以想象一个子类“Circle”,您知道图形应该是什么样子。然而,对于非常普通的“图形”,您不知道绘制它意味着什么


这就是为什么实际图形留在
抽象
类中的原因。因此,您不应该使
Figure
成为非抽象的,而应该通过实现
Figure
中的所有抽象方法,将重点放在从它扩展的类上,并使这些类成为非抽象的。在您的
类中,您知道
drawHere
应该做什么,所以在那里实现它以打印树。在另一个类中,如
Circle
,您以不同的方式实现它,但在
图中实现它从来没有真正意义,因为您不知道要绘制什么。

您可以为
drawHere()声明一个方法体。
(想必是空的,因为正如@Frank指出的,你真的不知道如何绘制一个
图形
)并删除
抽象的
修饰符。然后你就有了一个具体的类。这意味着有人可以创建一个
新图形()
。这不是您现在拥有的两个子类中的任何一个子类,只是一个


如果这样的对象(在调用<代码> Dead Dead()/代码>时不做任何事情)将是不有用的(特别是,如果您认为这样的对象是错误的),那么您应该保持类的抽象性。即使您可以为每个方法定义一个实现,这种推理也适用。

如果您有一个抽象类

public abstract class Figure
{
  private int offset;

  public Figure()
  {
    offset = 0;
  }

  public Figure(int theOffset)
  {
    offset = theOffset;
  }

  public void setOffset(int newOffset)
  {
    offset = newOffset;
  }

  public int getOffset()
  {
    return offset;
  }

  public abstract void drawHere();

  /**
   * Draws the figure at lineNumber lines down from the
   * current line.
   */

  public void drawAt(int lineNumber)
  {
    int count;
    for(count = 0; count < lineNumber; count++)
      System.out.println();
    drawHere();
  }
}
通过扩展和定义所讨论的抽象方法,可以针对各种条件分别定义行为

abstract class AbstractCar {

    float maxSpeed;
    Driver whoIsDriving;

    AbstractCar(float ms, Driver d) {
        maxSpeed = ms;
        if(!validateDriver(d)) throw new InvalidDriverException();
        whoIsDriving = d;
    }

    abstract boolean validateDriver(Driver d);

}

如果一个类是抽象的,你可以给所有的方法赋予主体,也可以不给任何方法赋予主体,但是如果任何一个类扩展了抽象类,它必须实现所有只声明的方法。

在Figure上扩展的两个类是Box和Triangle,它们不是抽象的。唯一抽象的类是Figure。我会创建一个方法吗这将绘制图形来代替“public abstract void drawHere();”,以最终删除抽象?这是为了强调抽象标记的易用性。是的,因此Box和Triangle提供了“draw here”的版本行为。不,你没有在抽象图形类中提供一个方法-你能明白为什么吗?只有当你知道一个默认行为可以应用于扩展它的所有子类时,这才有效。这对图形来说不可能是真的。看在上帝的份上,别管可怜的图形。不要碰它。
class CrappyCar extends AbstractCar {    
    boolean validateDriver(Driver d) {
        return d.hasLicense() && d.hasInsurance();
    }
}

class ExpensiveCar extends AbstractCar {
    boolean validateDriver(Driver d) {
        return d.hasLicense() && d.hasInsurance() && d.hasGoodJobInCaseHeMessesUpMyCar();
    }
}