相关疑难解决方法(0)

通过无效指针访问静态成员:保证"工作"?

建立

给定此用户定义的类型:

struct T
{
    static int x;
    int y;

    T() : y(38);
};
Run Code Online (Sandbox Code Playgroud)

并在某处有用的必要定义:

int T::x = 42;
Run Code Online (Sandbox Code Playgroud)

以下是将标准int值传递给stdout的规范方法:

std::cout << T::x;
Run Code Online (Sandbox Code Playgroud)

控制

同时,由于T不存在的实例,以下(当然)无效:

T* ptr = NULL; // same if left uninitialised
std::cout << ptr->y;
Run Code Online (Sandbox Code Playgroud)

现在考虑以下代码的可怕和邪恶和坏:

T* ptr = NULL;
std::cout << ptr->x; // remember, x is static
Run Code Online (Sandbox Code Playgroud)

ptr如上所述,取消引用无效.即使这里没有物理内存解除引用,我相信它仍然算作一个,使上面的代码UB.或者......是吗?

14882:2003 5.2.5/3明确表示a->b转换为(*(a)).b,并且:

评估点或箭头之前的后缀表达式; 即使结果不必确定整个后缀表达式的值,也会发生此评估,例如,如果id-expression表示静态成员.

但目前尚不清楚这里的"评估"是否涉及实际的解除引用.实际上,14882:2003和n3035似乎都没有明确地说明指针表达式在处理静态成员时是否必须求值为指向有效实例的指针.

我的问题是,这有多么无效?它是否真的被标准特别禁止(即使没有物理解除引用),或者它只是我们可以逃脱的语言的怪癖?即使它被禁止,我们还期望GCC/MSVC/Clang在多大程度上安全地对待它?

我的g ++ 4.4似乎生成的代码永远不会尝试将[invalid] this指针推入堆栈,并关闭优化.

BTW如果T是多态的,那么这不会影响这一点,因为静态成员不能是虚拟的.

c++

9
推荐指数
1
解决办法
862
查看次数

标签 统计

c++ ×1