使用在派生 类 中声明为纯虚拟的方法

using a method declared pure virtual in derived classes

我正在处理一段代码,我看到了一些奇怪的东西,一个 class "MyClass" 的方法我们称之为 X() :

virtual void X() = 0;

所以 MyClass 是一个抽象 class 并且在 MyClass.cpp 中 X() 有一个正确的实现... 在 MyClass 的派生 classes 中,此方法通过 MyClass::X();

调用

我认为 = 0 会使它的实现无效...但事实并非如此,事实上,它在派生的 classes 中可用。

请问编译器在遇到= 0时到底做了什么?

来自标准(9.2 Class成员[class.mem]):

= 0 is the pure-specifier

它告诉编译器:

  1. class是抽象
  2. 方法将在class定义之外定义 (通常在派生中class)

示例 1(构建失败)

如果我没有正确理解你的问题,那么你的问题是这样的:

class MyClass {
public:
    virtual void X() = 0;
};

class MyDerivedClass : MyClass {
public:
    virtual void X();
};

void MyDerivedClass::X() { MyClass::X(); }

int main()
{
    MyDerivedClass mdc;
    mdc.X();

    return 0;    
}

如果是这样,构建应该会失败:

错误:

undefined reference to 'MyClass::X()'

示例2(构建成功)

但是,即使方法 MyClass::X() 声明为 纯虚拟, 你可以提供一个定义。以下将起作用。 class MyClass 仍然是抽象,但是你可以调用方法MyClass::X().

#include <iostream>

class MyClass {
public:
    virtual void X() = 0; // pure virtual method
};

class MyDerivedClass : MyClass {
public:
    virtual void X();
};

void MyClass::X() {       // pure virtual method definition
    std::cout << "MyClass::X()" << std::endl;
}

void MyDerivedClass::X() {
    MyClass::X();
    std::cout << "MyDerivedClass::X()" << std::endl;
}  

int main()
{
    MyDerivedClass mdc;
    mdc.X();

    return 0;    
}

输出:

MyClass::X()
MyDerivedClass::X()

您无法使用纯虚方法创建 class 的实例,但在某些情况下您可以调用纯虚方法,它将是一个 error

我认为编译器会为纯虚方法创建一个带有 NULL 指针的 vtable。

=0 告诉编译器两件事:

  1. 不需要常规的 out-of-class 函数定义(尽管允许)。如果没有这样的定义,并且实际调用了该函数,则为runtine错误。
  2. class 是抽象的,无法实例化,无论第 1 点的定义是否存在。尝试这样做应该被标记为编译时错误。不覆盖函数的派生 classes 也是抽象的。