C++ 将void指针转换为特定类型指针时,哪个转换符号更好,static_cast或reinterpret_cast?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/5013596/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 17:10:18  来源:igfitidea点击:

When convert a void pointer to a specific type pointer, which casting symbol is better, static_cast or reinterpret_cast?

c++casting

提问by Sid Zhang

Possible Duplicate:
Should I use static_cast or reinterpret_cast when casting a void* to whatever

可能的重复:
在将 void* 转换为任何内容时,我应该使用 static_cast 还是 reinterpret_cast

In this program I have a void *as a parameter and want to cast it to a specific type. But I don't know which "casting symbol" to use. Both static_castor reinterpret_castwork. Which one is better? Which one does the Standard C++ recommend?

在这个程序中,我有一个void *作为参数,并希望将其转换为特定类型。但我不知道使用哪个“铸造符号”。两个static_castreinterpret_cast工作。哪一个更好?标准 C++ 推荐哪一种?

typedef struct
{
    int a;
}A, *PA;

int foo(void* a)                // the real type of a is A*
{
    A* pA = static_cast<A*>(a); // or A* pA = reinterpret_cast<A*>(a);?
    return pA->a;
}

Here, is

这是

A* pA = static_cast<A*>(a);

or

或者

A* pA = reinterpret_cast<A*>(a);

more proper?

更合适?

回答by templatetypedef

The static_castis more appropriate for converting a void*to a pointer of some other type.

static_cast是更合适的用于将void*一些其他类型的指针。

static_castis the cast of choice when there is a natural, intuitive conversion between two types that isn't necessarily guaranteed to work at runtime. For example, you can use static_castto convert base class pointers to derived class pointers, which is a conversion that makes sense in some cases but can't be verified until runtime. Similarly, you can use static_castto convert from an intto a char, which is well-defined but may cause a loss of precision when executed.

static_cast当两种类型之间存在自然、直观的转换但不一定保证在运行时工作时,是首选类型转换。例如,您可以使用static_cast将基类指针转换为派生类指针,这种转换在某些情况下是有意义的,但直到运行时才能进行验证。同样,您可以使用static_castto 从 an 转换int为 a char,这是定义明确的,但在执行时可能会导致精度损失。

reinterpret_cast, on the other hand, is a casting operator designed to do conversions that are fundamentally not safe or not portable. For example, you can use reinterpret_castto convert from a void *to an int, which will work correctly if your system happens to have sizeof (void*)sizeof (int). You can also use reinterpret_castto convert a float*to an int*or vice-versa, which is platform-specific because the particular representations of floats and ints aren't guaranteed to have anything in common with one another.

reinterpret_cast另一方面,是一个强制转换运算符,旨在进行从根本上不安全或不可移植的转换。例如,您可以使用reinterpret_cast将 a 转换void *为 an int,如果您的系统碰巧有sizeof (void*)≤ ,这将正常工作sizeof (int)。您还可以使用reinterpret_cast将 a 转换float*为 anint*或反之亦然,这是特定于平台的,因为floats 和ints的特定表示不能保证彼此之间具有任何共同点。

In short, if you ever find yourself doing a conversion in which the cast is logically meaningful but might not necessarily succeed at runtime, avoid reinterpret_cast. static_castis a good choice if you have some advance knowledge that the cast is going to work at runtime, and communicates to the compiler "I know that this might not work, but at least it makes sense and I have a reason to believe it will correctly do the right thing at runtime." The compiler can then check that the cast is between related types, reporting a compile-time error if this isn't the case. Using reinterpret_castto do this with pointer conversions completely bypasses the compile-time safety check.

简而言之,如果您发现自己进行的转换在逻辑上有意义但不一定在运行时成功,请避免reinterpret_cast. static_cast如果您对强制转换将在运行时工作有一些预先了解,并且与编译器进行通信,那么这是一个不错的选择“我知道这可能不起作用,但至少它是有道理的,我有理由相信它会正确在运行时做正确的事情。” 然后编译器可以检查强制转换是否在相关类型之间,如果不是这种情况,则报告编译时错误。使用reinterpret_cast指针转换来做到这一点完全绕过了编译时安全检查。

There are a few circumstances where you might want to use a dynamic_castinstead of a static_cast, but these mostly involve casts in a class hierarchy and (only rarely) directly concern void*.

在某些情况下,您可能想要使用 adynamic_cast而不是 a static_cast,但这些主要涉及类层次结构中的强制转换,并且(很少)直接关注void*.

As for which one is preferred by the spec, neither is overly mentioned as "the right one to use" (or at least, I don't remember one of them being mentioned this way.) However, I think the spec wants you to use static_castover reinterpret_cast. For example, when using a C-style cast, as in

至于规范更喜欢哪一个,两者都没有被过度提及为“正确使用的”(或者至少,我不记得其中一个被这样提及。)但是,我认为规范希望您使用static_castreinterpret_cast。例如,当使用 C 风格的强制转换时,如

A* ptr = (A*) myVoidPointer;

The order of casting operators that's tried always tries to use a static_castbefore a reinterpret_cast, which is the behavior you want since reinterpret_castisn't guaranteed to be portable.

尝试的转换运算符的顺序总是尝试在 astatic_cast之前使用a reinterpret_cast,这是您想要的行为,因为reinterpret_cast不能保证是可移植的。

回答by Asha

Use static_castfor this. Only in the rarest of rare cases when there is no other way use reinterpret_cast.

static_cast为此使用。仅在极少数情况下没有其他方法时才使用reinterpret_cast

回答by sharptooth

You likely obtained that void*with implicit conversion, so you should use static_castbecause it is closest to the implicit conversion.

您可能通过void*隐式转换获得了它,因此您应该使用static_cast它,因为它最接近隐式转换。

回答by Ken Wayne VanderLinde

If you are casting along a class hierarchy, use dynamic_cast- it checks to make sure that the actual object is compatible with the type to which you are casting.

如果您沿类层次结构进行转换,请使用dynamic_cast- 它检查以确保实际对象与您正在转换的类型兼容。

回答by mukeshkumar

reinterpret_castwill forcefully convert the void*to the target data type. It doesn't guarantee any safety and your program might crash as the underlying object could be anything.

reinterpret_cast将强制转换void*为目标数据类型。它不保证任何安全性,并且您的程序可能会崩溃,因为底层对象可能是任何东西。

For ex, you could typecast an myclass*to void*and then use reinterpret_castto convert it to yourclass*which may have a completely different layout.

例如,您可以对myclass*to 进行类型转换void*,然后使用reinterpret_cast将其转换为yourclass*可能具有完全不同的布局。

So its better and recommended to use static_cast

所以它更好,推荐使用 static_cast