在this answer的评论区与某人就他提出的建议争论时,我遇到了一些gcc4.8和VS2013无法编译但clang却能够愉快地接受并显示正确结果的代码。
#include <iostream>
int main()
{
int i{ 5 };
void* v = &i;
std::cout << reinterpret_cast<int&>(*v) << std::endl;
}
现场演示。GCC和VC都出现了我预期的错误,抱怨代码试图在reinterpret_cast
内解引用void*
。因此,我决定在标准中查找这个问题。从N3797开始,§5.2.10/11 [expr.reinterpret.cast]
在这种情况下,
T1
是void
,T2
是int
,可以使用reinterpret_cast
将void*
转换为int*
。因此,所有要求都得到满足。根据注释,
reinterpret_cast<int&>(*v)
的效果与*reinterpret_cast<int*>(&(*v))
相同,根据我的计算,这与*reinterpret_cast<int*>(v)
相同。那么这是GCC和VC的错误,还是clang和我误解了这个问题?
void* v = &i; *v;
会发生什么?clang 仍然不会抱怨。当将 void* 转换为其他类型时,我应该使用 static_cast 还是 reinterpret_cast 看起来很有趣。(警告:旧的信息可能已过时。) - user1508519&*ptr
看起来是合法的,但不等同于ptr
(我猜这就是你在最后一个reinterpret_cast
中想表达的)。因此,指针仍然需要被解引用。 - chris&*E
等同于E
。因此,这部分内容是正确的。我想剩下的问题是,如果E
是void
或者不完整类型会怎样? - Praetorianvoid *p; &*p;
如果是真正的noop,也应该可以正常工作。 - chris