const_cast vs reinterpret_cast
const_cast vs reinterpret_cast
参考c++常见问题解答何时应该使用static_cast、dynamic_cast和reinterpret_cast ?
const_cast用于向变量中删除或添加const,这是唯一可靠的、已定义的、合法的删除const的方法。Reinterpret_cast用于更改类型的解释。
我可以合理地理解为什么只使用const_cast将const变量强制转换为非const,但是我不能找出使用reinterpret_cast而不是const_cast来添加constness的合理理由。
我明白使用reinterpret_cast来添加constness是不理智的,但是使用reinterpret_cast来添加constness会是一个UB或潜在的定时炸弹吗?
我在这里感到困惑的原因是因为语句
在很大程度上,使用reinterpret_cast你得到的唯一保证是if您将结果强制转换回原始类型,您将得到精确的相同的值。
如果我用reinterpret_cast添加constness如果你用reinterpret_cast将结果转换回原始类型,它应该返回到原始类型而不应该是UB,但这违反了只能用const_cast删除constness的事实
另外,标准保证你可以使用reinterpret case 来添加Constness。5.2.10 Reinterpret cast (7) ......当将"指向T1的指针"类型的右值v转换为"指向cv T2的指针"类型时,结果为如果T1和T2都是,则static_cast(static_cast(v)标准布局类型(3.9)及T2的走线要求如下不严格于T1........
reinterpret_cast
更改对象内数据的解释。const_cast
添加或删除const
限定符。数据表示和一致性是正交的。所以使用不同的强制转换关键字是有意义的。
如果我用reinterpret_cast添加constness如果你用reinterpret_cast将结果转换回原始类型,它应该返回到原始类型而不应该是UB,但这违反了只能用const_cast删除constness的事实
甚至不能编译:
int * n = new int;
const * const_added = reinterpret_cast<const int *>(n);
int * original_type = reinterpret_cast<int*>(const_added);
// error: reinterpret_cast from type ‘const int*’ to type ‘int*’ casts away qualifiers
你不应该只是将const
与reinterpret_cast
相加。reinterpret_cast
应该主要是:重新解释指针(或其他)。
换句话说,如果你要从const char*
到char*
(希望是因为有一个不好的API你不能改变),那么const_cast
是你的朋友。这才是真正的目的。
但如果你需要从MyPODType*
到const char*
,你需要reinterpret_cast
,这只是很好,不需要const_cast
在上面
有一件事要记住:您不能使用const_cast
使const
变量可写。只有当const引用指向非const对象时,才能使用它从const引用中检索非const引用。听起来复杂吗?例子:
// valid:
int x;
int const& x1 = x;
const_cast<int&>(x1) = 0;
// invalid:
int const y = 42;
int const& y1 = y;
const_cast<int&>(y1) = 0;
实际上,这两种方法都可以编译,有时甚至可以"工作"。然而,第二种方法会导致未定义的行为,并且在许多情况下,当常量对象被放置在只读内存中时,将会终止程序。
也就是说,还有一些事情:reinterpret_cast
是最强大的施法,但也是最危险的一个,所以除非你必须使用它。当需要从void*
转到sometype*
时,使用static_cast
。当进行相反的方向时,使用内置的隐式转换或也使用显式的static_cast
。与添加或删除const
类似,它也是隐式添加的。关于reinterpret_cast
,请参见c++中的讨论:在什么情况下,我们应该更倾向于使用双链式static_cast而不是reinterpret_cast,其中讨论了一种不那么hackish的替代方法。
变成
我能想到的将reinterpret_cast与const-ness联系起来的唯一地方是将const对象传递给接受void指针的API -
UINT ThreadFunction(void* param)
{
const MyClass* ptr = reinterpret_cast<const MyClass*>(param);
}
是的,正如你所知道的,const_cast意味着它从特定类型中移除constness。
但是,当我们需要为类型添加constness时。我们一定要这么做吗?
例如
void PrintAnything(void* pData)
{
const CObject* pObject = reinterpret_cast<CObject*>(pData);
// below is bla-bla-bla.
}
reinterpret_cast与'const'无关。
const_cast意味着两件事。第一种方法是从类型中移除constness,另一种方法是赋予其代码显式性。因为你可以使用c风格的强制转换,但这不是显式的,所以不推荐使用。
它们的功能不同。
- 如何理解C++标准N3337中的expr.const.cast子句8
- C++Cast运算符过载
- 错误:"cast"未命名类型void setCastDescription(std::string
- 通过使用 const-cast 的非常量引用来延长临时的寿命
- "(void) cast"与功能有什么区别 "__attributes__"来沉默未使用的参数警告?
- C++:"Expected '(' for function-style cast or type construction"错误
- 为什么选择 g++ 给予者:"error: cast to pointer from integer of different size [-Werror=int-to-pointer-cast]"
- Gtk+ g_signal_connect() 和 C++ lambda 会导致"invalid cast"错误
- Shared_ptr cast vs static_cast speed
- C++20 中的严格别名规则是否允许标准 c++ unicode 字符和下划线类型之间"reinterpret
- 在 iOS 上使用 Aruco 构建 OpenCV 时"Functional-style cast from id to double is not allowed"
- 覆盖 CAST 运算符(我认为它被称为向下转换)
- C++错误,隐 <function-style-cast> 式要求使用模板化类一次调用多个构造函数的多个转换
- 如何修复<function-style-cast>错误:无法从'initializer list'转换为asdending比较<W>(模板函子)
- C++ C++ 中的函数声明,键入 CAST
- static_cast会丢弃错误,但C风格的演员cast有效
- C++ cast char * to unsigned char
- 禁用 Clang 中的"cast from pointer to smaller type uint32_t"错误
- 是否可以使用gcc 3.3版修复与int*cast相关的Sun Solaris OS 5.8分段故障
- C++ const-cast 一个引用