Re: MSDN const_cast sample
On Dec 18, 12:16 am, "Ben Voigt [C++ MVP]" <r...@nospam.nospam> wrote:
Otherwise, a compiler is non-compliant if casting away const doesn't
work.
Assuming this code:
void mutate( int const& i) {
const_cast<int&>(i) = 42;
}
int i = 5;
mutate(i);
std::cout << i << std::endl;
I would assume the compiler to behave properly and output 42. Do you know
of
any compilers that don't?
It should. It is only undefined behaviour if the variable/object being
modified was originally created as const. Here, i is not. And hence,
the modification should work. Don't know of a compiler that would go
against the above though.
I don't think "originally created as non-const" is sufficient.
For example:
void mutate( int const& i) {
const_cast<int&>(i) = 42;
}
void f(const int* const p)
{
int j = *p;
mutate(*p);
std::cout << *p << j << std::endl;
}
int i = 5;
f(&i);
I see no reason to believe that the compiler won't use the register used to
hold j instead of reading memory again. For that matter, it is probably
allowable to delay assigning a value to j until after the call to mutate.
No reason until there is no const_cast applied. Herb Sutter's
Exceptional C++ Item 43 (const-correctness) pg. 181 shows exactly
similar scenario and he mentions:
"Using the result of the const_cast is undefined if the referenced
object was declared as const...<snipped>" and later showing an example
as above mentions: "This is fine." So, you can modify an object of
type: a reference or pointer to const-qualified type that actually
does not refer or point to a const-qualified object using const_cast
to remove the const-ness. It is guaranteed to work.
I looked at the standards but it's wording is not clear to me and
hence I would back upon what EC++Item43 says. From the standards -
[expr.const.cast]/7:
[ Note: Depending on the type of the object, a write operation through
the pointer, lvalue or pointer to data member resulting from a
const_cast that casts away a const-qualifier68) may produce undefined
behavior (7.1.5.1). --end note ]
And from [dcl.type.cv]/3:
A pointer or reference to a cv-qualified type need not actually point
or refer to a cv-qualified object, but it is treated as if it does; a
const-qualified access path cannot be used to modify an object even if
the object referenced is a non-const object and can be modified
through some other access path. [ Note: cv-qualifiers are supported by
the type system so that they cannot be subverted without casting
(5.2.11). --end note ]
The note seems to hint that const_cast should work, that is how I
understood it. Could be wrong?