3

请参阅以下内容:

struct A
{
    std::string* get() const
    {
        //return const_cast<std::string*>(&m_pObj);
        return &const_cast<A*>(this)->m_pObj;
    }

    std::string m_pObj;
};

const_cast是取消引用thisUB吗?是否有任何时间取消引用const_cast指针的常量的结果不会调用 UB?

(我知道上面的例子是不好的做法,不好的设计,可以用 mutable 解决 - 这不是重点)

4

4 回答 4

9

是否取消引用此 UB 的 const_cast?是否有任何时间取消引用 const_casting 指针的 constness 的结果不会调用 UB?

并非总是如此,只有当对象const (A实例是const A x;并且取消引用用于修改数据时。如果它仅用于读取它不会是未定义的行为,如果对象不是 const,(可能根本不是,可能是对非 const 对象的 const 引用)它也不会是 UB。

于 2012-06-15T15:45:48.370 回答
3

const不,如果引用的对象已被声明为原始并且您随后修改了转换获得的数据(§5.2.11/7 和 §7.1.6.1/4),则它只是 UB 。以下是合法的:

A a;
a.get()->clear();

虽然这不是(因此是UB):

A const a;
a.get()->clear();
于 2012-06-15T15:44:43.067 回答
1

不。也就是说:

5.2.2 函数调用

5 [注意:函数可以更改其非常量参数的值,但这些更改不会影响参数的值,除非参数是引用类型(8.3.2);如果引用是 const 限定类型,则需要使用 const_cast 来丢弃 const 性以修改参数的值。如果参数是 const 引用类型,则在需要时引入临时对象(7.1.6、2.14、2.14.5、8.3.4、12.2)。此外,可以通过指针参数修改非常量对象的值。——尾注]

然而,

5.2.11 常量转换

12 [注意:某些仅涉及更改 cv 限定的转换不能使用 const_cast 完成。例如,函数指针之间的转换不包括在内,因为这种转换会导致使用导致未定义行为的值。出于同样的原因,指向成员函数的指针之间的转换,特别是从指向 const 成员函数的指针到指向非 const 成员函数的指针的转换,不包括在内。——尾注]

于 2012-06-15T15:46:29.883 回答
0

编译器可以自由地将 const 值存储在只读内存中,可以自由地假设在优化程序时它永远不会改变。如果你抛弃了 constness,你就违反了与编译器的约定,所以从技术上讲,任何事情都可能发生。

实际上,编译器很少会做一些会被 const_cast-ing 破坏的事情,但理论上这是可能的。

于 2012-06-15T15:57:23.567 回答