【发布时间】:2018-03-24 00:01:54
【问题描述】:
在我看来,以下程序应该崩溃,但它不仅可以工作而且显示正确的结果(“derv is called”)。
#include <iostream>
using namespace std;
class base
{
public:
virtual ~base(){}
};
class derv: public base
{
public:
void f() { cout << "derv is called" <<endl;}
};
int main() {
base* p = new base();
derv *d1 = dynamic_cast<derv*>(p);
// Since p point to base , so d1 should return nullptr
//calling any function using d1, should fail/crash
//but why the following line is working ??
d1->f();
}
抱歉,我忘记在上一篇文章中添加几行:如果我添加单个数据成员并尝试访问它,则会出现分段错误,我认为这是正确的行为。我的问题是为什么访问数据成员会改变行为?当变量未被访问时,调用“f()”函数成功,而同一个函数“f()”在使用数据成员访问时会出现分段错误?是未定义的行为吗?
class derv: public base
{
public:
int x = 0 ; // Added new member, c++11
void f() { cout << "derv is called " << x << endl;} //access it here
};
【问题讨论】:
-
你怎么知道
d1为空?您不检查它,并且您的函数不以任何方式使用this指针,因此即使它为空,它也有可能不会崩溃。 ideone.com/K2dTD7 这是一个崩溃:ideone.com/US5s6r -
这是未定义的行为。
-
再一次,未定义的行为意味着任何事情都可能发生——包括看起来“有效”。
-
C++ 中没有“应该崩溃”。如果您谈论的是具有特定标志、特定操作系统或特定内存情况的 C++ 编译器的特定实现,那么“应该崩溃”可能是有意义的。但是语言规范中没有强制崩溃。
标签: c++