在对任何内容进行void*时,是否应该使用static_cast或reviewt_cast ?

时间:2023-02-01 20:04:07

Both static_cast and reinterpret_cast seem to work fine for casting void* to another pointer type. Is there a good reason to favor one over the other?

static_cast和reinterpretation t_cast似乎都可以很好地将void*转换为另一个指针类型。有充分的理由偏爱其中一个吗?

4 个解决方案

#1


94  

Use static_cast: it is the narrowest cast that exactly describes what conversion is made here.

使用static_cast:这是最窄的cast,它准确地描述了这里的转换。

There’s a misconception that using reinterpret_cast would be a better match because it means “completely ignore type safety and just cast from A to B”.

有一种误解认为使用reinterpret_cast会是一个更好的匹配,因为它意味着“完全忽略类型安全性,只从a转换到B”。

However, this doesn’t actually describe the effect of a reinterpret_cast. Rather, reinterpret_cast has a number of meanings, for all of which holds that “the mapping performed by reinterpret_cast is implementation-defined.” [5.2.10.3]

然而,这实际上并没有描述reinterpret_cast的效果。相反,reinterpret_cast有很多含义,因为所有这些含义都包含“reinterpret_cast执行的映射是由实现定义的”。“(5.2.10.3)

But in the particular case of casting from void* to T* the mapping is completely well-defined by the standard; namely, to assign a type to a typeless pointer without changing its address.

但在从void*到T*的特定情况下,映射完全由标准定义;也就是说,在不更改其地址的情况下,将类型分配给无类型指针。

This is a reason to prefer static_cast.

这是选择static_cast的一个原因。

Additionally, and arguably more important, is the fact that every use of reinterpret_cast is downright dangerous because it converts anything to anything else really (for pointers), while static_cast is much more restrictive, thus providing a better level of protection. This has already saved me from bugs where I accidentally tried to coerce one pointer type into another.

此外,而且可以说更重要的是,reinterpret_cast的每一次使用都是非常危险的,因为它将任何东西转换为其他的东西(对于指针),而static_cast具有更多的限制性,因此提供了更好的保护级别。这已经使我避免了错误,在错误中我不小心试图强制一个指针类型到另一个。

#2


6  

This is a tough question. On the one hand, Konrad makes an excellent point about the spec definition for reinterpret_cast, although in practice it probably does the same thing. On the other hand, if you're casting between pointer types (as is fairly common when indexing in memory via a char*, for example), static_cast will generate a compiler error and you'll be forced to use reinterpret_cast anyway.

这是一个很难回答的问题。一方面,Konrad对于reinterpret_cast的规范定义提出了一个很好的观点,尽管在实践中它可能会做同样的事情。另一方面,如果您在指针类型之间进行强制转换(例如,通过char*在内存中建立索引是相当常见的),static_cast将生成编译器错误,您将*使用reinterpret_cast。

In practice I use reinterpret_cast because it's more descriptive of the intent of the cast operation. You could certainly make a case for a different operator to designate pointer reinterprets only (which guaranteed the same address returned), but there isn't one in the standard.

在实践中,我使用reinterpretation t_cast,因为它更加描述了cast操作的意图。您当然可以为一个不同的操作符创建一个实例来指定指针重新解释(它保证返回相同的地址),但是在标准中没有一个。

#3


2  

I suggest using the weakest possible cast always.

我建议尽量使用最弱的石膏。

reinterpret_cast is may be used to cast a pointer to a float. The more structure-breaking cast is, the more attention using it requires.

reinterpretation t_cast可以用来将指针转换为浮点数。越是破坏结构的铸型,就越需要更多的关注。

In case of char*, I'd use c-style cast, until we have some reinterpret_pointer_cast, because it's weaker and nothing else is sufficient.

对于char*,我将使用c样式的cast,直到我们有reinterpret_pointer_cast,因为它比较弱,其他的都是不够的。

#4


-3  

My personal preference is based on code literacy like this:

我个人的偏好是基于这样的代码读写能力:

void* data = something;
MyClass* foo = reinterpret_cast<MyClass*>(data);
foo->bar();

or

typedef void* hMyClass; //typedef as a handle or reference
hMyClass = something;
const MyClass& foo = static_cast<MyClass&>(*hMyClass);
foo.bar();

They both do the same in the end, but static_cast seems more appropriate in a middle-ware, app enviroment, while reinterpret cast seems more like something you'd see in a lower-level library IMHO.

他们最后都做了同样的事情,但是static_cast似乎更适合在中级软件,应用环境中,而reinterpretation cast更像是在低级库IMHO中看到的东西。

#1


94  

Use static_cast: it is the narrowest cast that exactly describes what conversion is made here.

使用static_cast:这是最窄的cast,它准确地描述了这里的转换。

There’s a misconception that using reinterpret_cast would be a better match because it means “completely ignore type safety and just cast from A to B”.

有一种误解认为使用reinterpret_cast会是一个更好的匹配,因为它意味着“完全忽略类型安全性,只从a转换到B”。

However, this doesn’t actually describe the effect of a reinterpret_cast. Rather, reinterpret_cast has a number of meanings, for all of which holds that “the mapping performed by reinterpret_cast is implementation-defined.” [5.2.10.3]

然而,这实际上并没有描述reinterpret_cast的效果。相反,reinterpret_cast有很多含义,因为所有这些含义都包含“reinterpret_cast执行的映射是由实现定义的”。“(5.2.10.3)

But in the particular case of casting from void* to T* the mapping is completely well-defined by the standard; namely, to assign a type to a typeless pointer without changing its address.

但在从void*到T*的特定情况下,映射完全由标准定义;也就是说,在不更改其地址的情况下,将类型分配给无类型指针。

This is a reason to prefer static_cast.

这是选择static_cast的一个原因。

Additionally, and arguably more important, is the fact that every use of reinterpret_cast is downright dangerous because it converts anything to anything else really (for pointers), while static_cast is much more restrictive, thus providing a better level of protection. This has already saved me from bugs where I accidentally tried to coerce one pointer type into another.

此外,而且可以说更重要的是,reinterpret_cast的每一次使用都是非常危险的,因为它将任何东西转换为其他的东西(对于指针),而static_cast具有更多的限制性,因此提供了更好的保护级别。这已经使我避免了错误,在错误中我不小心试图强制一个指针类型到另一个。

#2


6  

This is a tough question. On the one hand, Konrad makes an excellent point about the spec definition for reinterpret_cast, although in practice it probably does the same thing. On the other hand, if you're casting between pointer types (as is fairly common when indexing in memory via a char*, for example), static_cast will generate a compiler error and you'll be forced to use reinterpret_cast anyway.

这是一个很难回答的问题。一方面,Konrad对于reinterpret_cast的规范定义提出了一个很好的观点,尽管在实践中它可能会做同样的事情。另一方面,如果您在指针类型之间进行强制转换(例如,通过char*在内存中建立索引是相当常见的),static_cast将生成编译器错误,您将*使用reinterpret_cast。

In practice I use reinterpret_cast because it's more descriptive of the intent of the cast operation. You could certainly make a case for a different operator to designate pointer reinterprets only (which guaranteed the same address returned), but there isn't one in the standard.

在实践中,我使用reinterpretation t_cast,因为它更加描述了cast操作的意图。您当然可以为一个不同的操作符创建一个实例来指定指针重新解释(它保证返回相同的地址),但是在标准中没有一个。

#3


2  

I suggest using the weakest possible cast always.

我建议尽量使用最弱的石膏。

reinterpret_cast is may be used to cast a pointer to a float. The more structure-breaking cast is, the more attention using it requires.

reinterpretation t_cast可以用来将指针转换为浮点数。越是破坏结构的铸型,就越需要更多的关注。

In case of char*, I'd use c-style cast, until we have some reinterpret_pointer_cast, because it's weaker and nothing else is sufficient.

对于char*,我将使用c样式的cast,直到我们有reinterpret_pointer_cast,因为它比较弱,其他的都是不够的。

#4


-3  

My personal preference is based on code literacy like this:

我个人的偏好是基于这样的代码读写能力:

void* data = something;
MyClass* foo = reinterpret_cast<MyClass*>(data);
foo->bar();

or

typedef void* hMyClass; //typedef as a handle or reference
hMyClass = something;
const MyClass& foo = static_cast<MyClass&>(*hMyClass);
foo.bar();

They both do the same in the end, but static_cast seems more appropriate in a middle-ware, app enviroment, while reinterpret cast seems more like something you'd see in a lower-level library IMHO.

他们最后都做了同样的事情,但是static_cast似乎更适合在中级软件,应用环境中,而reinterpretation cast更像是在低级库IMHO中看到的东西。