Java vtable用于超级方法

时间:2018-12-03 23:02:44

标签: java jvm dynamic-dispatch

当我们有两个班级时:

https://cdn.example.com

和:

class Foo {
    void foo() {
        System.out.println("foo");
    }
}

Bar clazz对象是否在vtable中存储对foo()和bar()方法的引用,还是在Bar vtable中仅对bar()方法的引用,并且要访问foo()方法jvm访问Bar clazz对象,然后是Foo clazz对象,然后在其vtable中找到foo()方法? 它更像这样: enter image description here 或者那个: enter image description here 或者也许这没有在规范中描述,并且可能取决于JVM的实现?

1 个答案:

答案 0 :(得分:4)

JVM规范没有规定如何实现虚拟方法调用。它甚至没有提到 vtable 的概念。 JVM实现可以选择这种方式或其他方式,只要它的行为符合预期即可。

对于Java SE虚拟机的参考实现HotSpot JVM,它的工作原理与您的第一幅图类似,即,一个类的单个vtable包含其所有虚拟方法,包括继承的虚拟方法。

     ------------------      ------------------ 
    | Foo.class vtable |    | Bar.class vtable |
    |------------------|    |------------------|
    | clone            |    | clone            | \
    | equals           |    | equals           | | java.lang.Object
    | hashCode         |    | hashCode         | / virtual methods
    | ...              |    | ...              |
    | foo              |    | foo              | } Foo virtual methods
     ------------------     | bar              | } Bar virtual methods
                             ------------------

这种布局可确保Foo类的所有后代在vtable中的同一索引处都具有对foo方法的引用。这样一来,即使是使用巨形方法,也可以在固定时间内进行足够快的虚拟调用。