![](/i/fill.gif) |
![](/i/fill.gif) |
|
![](/i/fill.gif) |
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
Darren New <dne### [at] san rr com> wrote:
> On 5/14/2011 0:40, Warp wrote:
> > For example, in C the only way to make an explicit cast is using the
> > syntax "(type) variable". However, C++ added the possibility of writing
> > such casts as "type(variable)". This allows for 'type' to not only be a
> > basic type, but also a class (in which case it would be a constructor
> > call).
> That's cool. I'm still not sure whether to like C++ or hate it. ;-)
> So what's the static_cast<...> bit all about, then? Is that just something
> easy to grep for, or does it have different semantics than a regular cast?
The C-style cast will cast from anything to anything else. Hence it's
not the safest thing in the world, as it's relatively easy to miscast and
have your program misbehave.
static_cast will only work between compatible types. For example you can
cast an int to a char, a signed int to an unsigned int, classes to other
classes within their inheritance hierarchy, and so on. However, if you try
to static_cast between incompatible types, you will get a compiler error.
For example, you can't cast an int to a pointer, a const pointer to a
non-const one (even if the pointers are of the same type) or between classes
not in direct inheritance relationship.
It is thus recommended to use static_cast instead of C style casts
whenever possible. Incidentally (but not surprisingly), if you use
static_cast to cast some variable to a class type, and that class has
a constructor that takes a value of that type, it will work. (It will
be the same as constructing the object with the regular syntax.) Supporting
the C style of casting exists more or less just for compatibility with C
code (which of course means that many C++ programmers are using it instead
of static_cast because it's shorter and more "convenient").
To cast constness away between compatible types const_cast should be
used. (It's basically its only role.)
To cast between incompatible types reinterpret_cast should be used.
(It assumes you know what you are doing.)
reinterpret_cast should *not* be used to cast between pointers to objects
in the same inheritance hierarchy because it may forgo adjusting the pointer
offset which may be necessary in some situations.
--
- Warp
Post a reply to this message
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
Am 14.05.2011 18:34, schrieb Darren New:
> On 5/14/2011 0:40, Warp wrote:
>> For example, in C the only way to make an explicit cast is using the
>> syntax "(type) variable". However, C++ added the possibility of writing
>> such casts as "type(variable)". This allows for 'type' to not only be a
>> basic type, but also a class (in which case it would be a constructor
>> call).
>
> That's cool. I'm still not sure whether to like C++ or hate it. ;-)
>
> So what's the static_cast<...> bit all about, then? Is that just
> something easy to grep for, or does it have different semantics than a
> regular cast?
"5.2.9 Static cast [expr.static.cast]
1 The result of the expression static_cast<T>(v) is the result of
converting the expression v to type T. If T is a
reference type, the result is an lvalue; otherwise, the result is an
rvalue. Types shall not be defined in a static_cast.
THE STATIC_CAST OPERATOR SHALL NOT CAST AWAY CONSTNESS (5.2.11)."
(emphasis added)
I.e. the static_cast of a const pointer remains a const pointer. It is
therefore a good idea to always use static_cast instead of a classic
cast, as it prevents accidental "stripping" of the const property;
consider, for instance, the following code:
void foo(int* x);
void bar(void* x) {
...
foo((int*)x);
...
}
Now assume the code is refactored to use const qualifiers, but for some
reason the cast in the call to foo() goes unnoticed:
void foo(const int* x);
void bar(const void* x) {
...
foo((int*)x);
...
}
Now assume a functionality change requires foo() to modify its parameter:
void foo(int* x);
void bar(const void* x) {
...
foo((int*)x);
...
}
The code still compiles, so it goes unnoticed that the function
signature of bar() is now actually wrong.
If the original code author had used static_cast instead, the mistake
would have been detected by the compiler, as the following code raises
an error due to mismatching const qualifiers:
void foo(int* x);
void bar(const void* x) {
...
foo(static_cast<int*>x);
...
}
Post a reply to this message
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
On 5/15/2011 1:00, Warp wrote:
> static_cast will only work between compatible types.
Ah, cool. Again, thanks for the info!
--
Darren New, San Diego CA, USA (PST)
"Coding without comments is like
driving without turn signals."
Post a reply to this message
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |
|
![](/i/fill.gif) |
| ![](/i/fill.gif) |
|
![](/i/fill.gif) |