c++ - 了解 Google 的 V8 C++ 代码库中的继承

标签 c++ inheritance architecture v8

我无法理解 Google 的 V8 JavaScript 引擎中继承的实现。它显然(?)实现了继承层次结构,但似乎完全取消了虚函数。

这是 objects.h header file 中详述的继承层次结构:

// Inheritance hierarchy:
// - Object
//   - Smi          (immediate small integer)
//   - HeapObject   (superclass for everything allocated in the heap)
//     - JSReceiver  (suitable for property access)
//       - JSObject
//         - JSArray
// ... and many more entries

大多数对象类型都派生自Object,声明如下:

// Object is the abstract superclass for all classes in the
// object hierarchy.
// Object does not use any virtual functions to avoid the
// allocation of the C++ vtable.
// Since both Smi and HeapObject are subclasses of Object no
// data members can be present in Object.
class Object {
// ... bunch of method declarations and definitions
};

接下来声明相对简单的Smi类:

class Smi: public Object {
 public:
 // methods declarations and static member definitions
};

等等。

在我的生活中,我无法理解,比方说,Smi 的实例如何可以用作Object没有虚函数并且我在the implementation file, objects.cc中找不到覆盖。但是,在 17,290 行中,试图了解正在发生的事情被证明是一项艰巨的任务。

作为另一个困难,我在同一个头文件中找到了一个 ObjectVisitor 类(这个更经典;它由虚拟方法组成)。但是我在 Object 基类中找不到等效的 Accept(Visitor*) (或类似的)方法。

我具体要问的是一个最小的例子来说明这种继承模式是如何工作的。

最佳答案

objects.h 中的类实际上并没有定义真正的 C++ 类。他们没有任何领域。这些类仅仅是 V8 JavaScript 堆上管理的对象的外观。因此它们也不能有任何虚函数,因为那需要将 vtable 指针放入 JS 堆中。相反,所有分派(dispatch)都是通过显式类型检查和向下转换手动完成的。

方法中的 this 指针也不是真实的。对于 smis,this 只是一个整数。对于其他所有内容,它都是一个指向 V8 堆的指针,为了标记而减一。任何实际的访问器方法都会屏蔽此指针并添加偏移量以访问堆中的适本地址。每个字段的偏移量也在类中手动定义。

关于c++ - 了解 Google 的 V8 C++ 代码库中的继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31506379/

相关文章:

C++:尝试在二进制到十进制转换器中多次将非常大的整数加在一起,而您的输入是字符串值

python - 将 Python 脚本实现为 C++

c++ - 构建 Qt 应用程序时为 "/usr/bin/ld: cannot find -lGL"

c++ - 在没有 new[] : Pointer to Base vtable is bad 的情况下分配 Derived 数组

c++ - 尽管在派生类中有定义,但基类中的方法不可见;多态性和使用 `virtual` 关键字

java - java类存储在数据库的哪里?

java - 选择分布式共享内存解决方案

java - 当您想要删除重复代码时,如何解决项目的循环依赖?

c# - 使用接口(interface)引用变量调用基类方法

asp.net - 从 DAL 返回什么到 BLL