Переменные могу интерпретироваться как const?

Рейтинг: 2Ответов: 1Опубликовано: 16.01.2023

Смотрел где хранятся локальные константы, и там был похожий пример, который изменял константу:

const int x = 1;
int* ptr = const_cast<int*>(&x);
*ptr = 45;
std::cout << *const_cast<int*>(&x);

И у меня возник вопрос, почему при прямом выводе x, значение остается 1? Из-за того что x интерпретируется как const int?

Ответы

▲ 2Принят

Снять константность можно лишь в тех случаях, когда исходный объект не был константным.

int x = 1;
const int* cptr = &x;
int* ptr = const_cast<int*>(cptr);
*ptr = 45;
cout << *ptr << '\n' << *cptr << '\n' << x << '\n';

Тут все нормально, так как сам x не константный, но пришлось работать с указателем, посредством которого невозможно было изменить его значение. (Ваш пример компилятор мог бы интерпретировать(изменить) таким образом, или вообще другим образом(это на его усмотрение), поэтому в результате будет неопределенное поведение).

Или, скажем, другой пример(даже самый наивный чисто для демонстрации):

struct SomeType {
    
     SomeType(int y = 1) : x(y){}
     const int* getptr() { return &x; }
 private:
     int x;
 };

Тут геттер SomeType::getptr по хорошему должен быть константным(const int* getptr() const ), чтобы для константных экземпляров вызвать член, который не меняет состояние объекта. В данном виде для объекта const SomeType obj(3) не сможем вызвать этот член, но мы точно знаем, что данная функция_член не пытается изменять его состояние, поэтому можем все же вызвать этот метод для него, сняв константность. Вот пример:

cout << *const_cast<SomeType*>(&obj)->getptr();

P.S. Любой инструмент имеет свое предназначение, и плохая привычка пытаться использовать его где попало...