I know the reinterpret_cast in C++ can be used in this way:
float a = 0;
int b = *reinterpret_cast(&a);
Bu
why cannot cast it directly?
I believe that this is a pure design decision, to make C++ more type-safe than C.
reinterpret_cast
is very dangerous, because it can involve type aliasing which is a short way to undefined behavior. When you use C++ casts, you sign a contract with your compiler "I know, what I am doing". So, all these long operators names, angle brackets, type-pointer-type conversions telling you: "Wait, don't do it. Maybe there is something wrong in your code design!".
Also, not all C++ compilers allow type aliasing (either achieved by casting or by unions).
You can't reinterpret_cast in the case you give because reinterpret_cast takes only either a int to convert to a pointer, or the reverse, and follows additional similar rules.
There is a summary of these rules there: http://en.cppreference.com/w/cpp/language/reinterpret_cast
With reinterpret_cast
you can cast a pointer type to any other pointer type, for example
you can cast float
pointer to int
pointer:
float *a = new int(0);
int* b = reinterpret_cast<int*>(a);
All reinterpret_cast
does is allow you to read the memory you passed in a different way. You give it a memory location and you ask it to read that memory as if it was what you asked it to. This is why it can only be used with pointers and references.
Let's take this code as an example:
#include <iostream>
int main()
{
float a = 12;
int b = *reinterpret_cast<int*>(&a);
std::cout << b;
}
So to break this line of code into more details *reinterpret_cast<int*>(&a);
:
a
reinterpret_cast
to an int*
int*
that points to a
int
Now when I run this I get 1094713344
, the reason for that is 12 as a float
using IEEE is represented as 0100 0001 0100 0000 0000 0000 0000 0000
in binary. Now take that binary and read it as unsigned int
, then you end up with 1094713344
.
This is why reinterpret_cast
is considered to be very dangerous and why it should NOT be used in this type of cases.
You should only use it when you have a pointer pointing to memory and you need to read that memory in a certain way and you know that the memory can be read in that way.
In the second case, it is not a cast from the value a
to b
. In fact, that is just a conversion. b
will not point to x
and pretend that it points to a float. Conversion constructs a new value of type int and assigns it the value from a
.
There are several ways to do this conversion correctly in C++.
One is simply to use static cast as usual. This is the recommended solution:
int b = static_cast<int>(a);
You could use reinterpret_cast in the following way below. Note this is doing the reinterpretation for the bit patter, and not conversion unlike the alternatives mentioned:
int b = reinterpret_cast<int&>(a);
You could also use the C style cast:
int b = (int)a;
You could also use the C++ function style casting:
int b = int(a);
You could get the implicit conversation as well, albeit it might generate a warning:
int b = a;
The static cast is recommended in this special case, but at least do not use the implicit conversation, nor the C style in C++.