Code:
char keyStr[50]={ 0x5F, 0x80 /* bla bla */ };
uint32_t* reCast = reinterpret_cast< uint32_t* >( &keyStr[29] );
uint32_t* reCast2 = ( uint32_t* )
reinterpret_cast
and const_cast
are ways of getting around the C++ type system. As you noted for reinterpret_cast
, this usually translates to little or no assembly code.
static_cast
mostly respects the C++ type system. It could convert a number from one type to another, or call a constructor, or call a conversion function. Or for a derived-to-base conversion, it might involve adding byte offsets and/or lookups into a vtable. static_cast
can also bend the type system's rules by "downcasting" a pointer or reference from a non-virtual base type to a derived type, possibly subtracting a byte offset.
And then there are pointers-to-member. They're probably beside the point here, but static_cast
does things to them more or less analogous to class pointer conversions.
dynamic_cast
respects the C++ type system even more strictly. In its useful form, it checks at runtime whether or not a pointer/reference actually points/refers to an object of the specified type. It typically calls a magic library function under the covers.
A function-style cast with one argument has exactly the same effect as a C-style cast. (With more than one argument, a function-style cast must be a temporary initialization using a class constructor.) A C-style cast does the first thing that makes sense out of the following list:
const_cast
static_cast
static_cast
and then a const_cast
reinterpret_cast
, orreinterpret_cast
and then a const_cast
One exception: C-style casts can ignore private and protected inheritance relations between classes, pretending they have a public inheritance relation instead.
C-style casts are usually not preferred in C++ because it's less specific about what you want to happen.