MST

星途 面试题库

面试题:Java抽象类的方法重写与多态实现细节

假设存在一个Java抽象类`Shape`,其中定义了抽象方法`calculateArea`用于计算图形面积。现有`Circle`和`Rectangle`两个子类继承自`Shape`,请详细描述在这两个子类中重写`calculateArea`方法的具体要求,以及如何利用多态性在主程序中实现根据不同的图形对象调用相应的`calculateArea`方法来获取正确的面积值,并分析在这个过程中涉及到的Java虚拟机机制。
36.5万 热度难度
编程语言Java

知识考点

AI 面试

面试题答案

一键面试
  1. 子类重写calculateArea方法的要求
    • 方法签名必须一致:在CircleRectangle子类中,calculateArea方法的返回类型、方法名和参数列表必须与Shape抽象类中的抽象方法calculateArea完全一致。因为Shape类中calculateArea是抽象方法,没有方法体,所以在CircleRectangle子类中必须提供具体的实现。
    • 访问修饰符不能更严格CircleRectangle子类中calculateArea方法的访问修饰符不能比Shape类中抽象方法的访问修饰符更严格。例如,如果Shape类中calculateArea方法是protected,那么在子类中可以是protectedpublic,但不能是private
  2. 利用多态性在主程序中实现获取面积值
    • 代码示例
abstract class Shape {
    public abstract double calculateArea();
}

class Circle extends Shape {
    private double radius;
    public Circle(double radius) {
        this.radius = radius;
    }
    @Override
    public double calculateArea() {
        return Math.PI * radius * radius;
    }
}

class Rectangle extends Shape {
    private double width;
    private double height;
    public Rectangle(double width, double height) {
        this.width = width;
        this.height = height;
    }
    @Override
    public double calculateArea() {
        return width * height;
    }
}

public class Main {
    public static void main(String[] args) {
        Shape circle = new Circle(5);
        Shape rectangle = new Rectangle(4, 6);
        System.out.println("Circle area: " + circle.calculateArea());
        System.out.println("Rectangle area: " + rectangle.calculateArea());
    }
}
  • 解释:在主程序中,定义了Shape类型的变量circlerectangle,但分别指向CircleRectangle的实例。这就是多态性的体现,即相同的方法调用(calculateArea),根据对象的实际类型(CircleRectangle),调用相应子类的calculateArea方法,从而获取正确的面积值。
  1. 涉及到的Java虚拟机机制
    • 动态绑定:在运行时,Java虚拟机根据对象的实际类型来确定调用哪个方法。在上述例子中,当调用circle.calculateArea()时,Java虚拟机知道circle实际指向的是Circle对象,所以调用Circle类中的calculateArea方法;当调用rectangle.calculateArea()时,因为rectangle实际指向Rectangle对象,所以调用Rectangle类中的calculateArea方法。这种动态绑定机制使得Java能够实现多态性。
    • 方法表:Java虚拟机为每个类维护一个方法表,方法表中记录了类及其父类中所有可被调用的方法的实际地址。当对象调用方法时,Java虚拟机通过对象的实际类型找到对应的方法表,然后根据方法表中记录的地址调用具体的方法。例如,Circle对象调用calculateArea方法时,Java虚拟机在Circle类的方法表中找到calculateArea方法的实际地址并执行该方法。