C++运行时多态为什么编译时不能确定

http://www.voidcn.com/article/p-gkjduiyi-bsm.html
考虑:

#include
using namespace std;
class Base
{
    public:
        virtual void show() { cout<<" In Base \n"; }
};

class Derived: public Base
{
    public:
       void show() { cout<<"In Derived \n"; }
};

int main(void) {
    Base *bp = new Derived;
    bp->show();  // RUN-TIME POLYMORPHISM
    return 0;
}

为什么这段代码导致运行时多态性,为什么不能在编译时解决?

因为在一般情况下,在编译时不可能确定在运行时将是什么类型。您的示例可以在编译时解决(请参阅@Quentin的回答),但是可以构造不能的案例,例如:

Base *bp;
if (rand() % 10 < 5)
    bp = new Derived;
else
    bp = new Base;
bp->show(); // only known at run time

这里有一个更好的情况。就像是:

Base *bp;
char c;
std::cin >> c;
if (c == 'd')
    bp = new Derived;
else
    bp = new Base;
bp->show(); // only known at run time

此外,由于推论[Turing’s proof](javascript:void()),可以表明在一般情况下,C编译器在数学上不可能知道基类指针在运行时指向什么。

假设我们有一个类似C编译器的函数:

bool bp_points_to_base(const string& program_file);

这需要输入program_file:任何C源代码文本文件的名称,其中指针bp(如在OP中)调用其虚拟成员函数show()。并且在一般情况下(在序列点A处,其中虚拟成员函数show()首先通过bp被调用):指针bp是否指向Base的实例。

考虑下面的C程序“q.cpp”的片段:

Base *bp;
if (bp_points_to_base("q.cpp")) // invokes bp_points_to_base on itself
    bp = new Derived;
else
    bp = new Base;
bp->show();  // sequence point A

你可能感兴趣的:(C++运行时多态为什么编译时不能确定)