sha*_*oth 57 c++ pointers static-members undefined-behavior dereference
我在几个旧项目中看到过这样的代码:
class Class {
static void Method() {}
};
((Class*)0)->Method();
Run Code Online (Sandbox Code Playgroud)
此代码包含未定义的行为,因为它包括取消引用空指针(无论之后发生什么).这真的没有意义 - 演员是在那里将类型名称提供给编译器,并且编写上面代码的人可以写这个:
Class::Method();
Run Code Online (Sandbox Code Playgroud)
而后者也没关系.
为什么有人会写前代码?它是来自一些美好时光的已知成语还是什么?
eca*_*mur 67
静态成员函数在1989年的AT + T C++语言系统2.0版(预标准化)中被添加到C++中.在此之前,static
关键字不能用于声明静态成员函数,因此代码作者使用了变通方法,主要是您观察到的间接空指针的变通方法.
在AT&T C++语言系统2.0版附带的选读中,在第1-22节中,Stroustrup写道:
还观察到不可移植的代码,例如:
Run Code Online (Sandbox Code Playgroud)((X*)0)->f();
用于模拟静态成员函数.这个技巧是一个定时炸弹,因为迟早有人会以
f()
这种方式使用它virtual
,并且呼叫将失败,因为X
零地址没有对象.即使在f()
虚拟的地方,这种调用也会在动态链接的某些实现中失败.
您的代码是在Cfront 1.0下编写的,或者是在向该语言添加静态成员函数时不知道的人编写的.
成员函数的注释static
确实是一个难题,如Cheers和hth.- 阿尔夫观察到了; Cfront 1.0会拒绝该代码:
error: member Method() cannot be static
Run Code Online (Sandbox Code Playgroud)
所以它最初不可能存在.我认为Potatoswatter最可能是正确的; 一旦C++ 2.0编译器可以保证可用,但没有更新调用代码,就会static
在以后添加文档并强制执行静态方法属性Method
.要确认这一点,您需要采访原始程序员或至少检查源控制历史记录(如果存在).