我应该在使用static_cast或reinterpret_cast时将void *转换为任何内容
static_cast和reinterpret_cast似乎都能很好地将void *转换为另一个指针types。 有一个很好的理由相互赞成吗?
使用static_cast
:这是最精确的转换,它描述了在这里进行的转换。
有一个误解,认为使用reinterpret_cast
将是一个更好的匹配,因为它意味着“完全忽略types安全,只是从A到B”。
但是,这实际上并没有描述reinterpret_cast
的效果。 相反, reinterpret_cast
具有许多含义,所有这些含义认为“ reinterpret_cast
执行的映射是实现定义的”。[5.2.10.3]
但是在从void*
到T*
的特定情况下,映射完全由标准定义; 即将types分配给无types指针而不改变其地址。
这是偏好static_cast
的原因。
此外,可以说更重要的是, reinterpret_cast
每一次使用都是非常危险的,因为它将任何东西都转换成真正的(指针),而static_cast
则更加严格,从而提供更好的保护。 这已经把我从错误中救了出来,我不小心试图强制一个指针types到另一个指针types。
这是一个棘手的问题。 一方面,康拉德对reinterpret_cast的规格定义提出了一个很好的观点,尽pipe实际上它可能做同样的事情。 另一方面,如果要在指针types之间进行转换(例如,在通过char *在内存中进行索引时相当常见), static_cast将生成编译器错误,无论如何您将被迫使用reinterpret_cast 。
在实践中,我使用reinterpret_cast,因为它更多地描述了投射操作的意图。 你当然可以为不同的操作符指定指针重新解释(保证返回相同的地址),但标准中没有一个。
我build议总是使用最弱的投。
reinterpret_cast可能被用来把一个指针转换成一个浮点数。 越是破坏性的angular色,使用它就越需要关注。
在char *的情况下,我会使用C风格的演员,直到我们有一些reinterpret_pointer_cast,因为它更弱,没有其他的东西是足够的。
我个人的偏好是基于这样的代码素养:
void* data = something; MyClass* foo = reinterpret_cast<MyClass*>(data); foo->bar();
要么
typedef void* hMyClass; //typedef as a handle or reference hMyClass = something; const MyClass& foo = static_cast<MyClass&>(*hMyClass); foo.bar();
他们最后都做了同样的事情,但static_cast似乎更适合在中间件,应用程序的环境,而重新解释演员似乎更像是你在一个更低级别的图书馆恕我直言,看到的东西。