Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.73/11: Рейтинг темы: голосов - 11, средняя оценка - 4.73
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826

Изменение константного поля класса

04.12.2015, 12:55. Показов 2149. Ответов 5
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Является ли изменение константы-поля класса UB?
- компилятор может закэшировать значение и не ждать, что оно другое.
- с другой стороны это поле класса с классификатором volatile
- и если сделать virtual T getConst() const - то ведь никакая оптимизация тут не пройдет(если компилятор тупой и не заметит, что нету наследника) - runtime взятие объязует его ходить за константой каждый раз.


Вопрос: Можно ли считать данный код
http://rextester.com/DLQO97167
Кликните здесь для просмотра всего текста
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#include <iostream>
using namespace std;
 
template <typename t>
union reinstallableconst;
 
class constchanger
{
public:
   template <typename t>
   static void change( reinstallableconst<t>& obj, const t& newvalue )
   {
      obj._modifyconst = newvalue;
   }
};
 
template <typename t>
union reinstallableconst
{
   reinstallableconst() :
      _get( 0 )
   {
   }
   reinstallableconst( const int constsetvalue ) :
      _get( constsetvalue )
   {
   }
 
private:
   t _modifyconst;
   friend void constchanger::change<t>( reinstallableconst<t>& obj, const t& newvalue );
public:
   const volatile t _get;
};
 
 
 
 
 
 
int main()
{
   reinstallableconst<int> speed( 199 );
 
   cout << speed._get << endl;
   //speed._get = 15;                                 // error: assign to a variable that is const
 
   constchanger::change<int>( speed, 51 );
   cout << speed._get << endl;
 
}


а) теоретически злым и UB
б) практически рабочим и кроссплатформенным, с гарантией работы
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
04.12.2015, 12:55
Ответы с готовыми решениями:

Изменение константного объекта с применением const_cast
1. Это код из учебника С. Прата &quot;Лекции и упражнения&quot;. #include &lt;iostream&gt; using namespace std; void change(const int* pt,...

Инициализация константного статического объекта - члена класса
Здравствуйте, у меня возникла проблема с инициализацией статического объекта, который является членом класса. Этот объект должен быть...

Инициализация константного члена класса с проверкой значения
Допустим есть класс константным членом class a{ const int i; public: a(int ii):i(ii){}; } Можно ли как-нибудь...

5
19491 / 10097 / 2460
Регистрация: 30.01.2014
Сообщений: 17,805
04.12.2015, 12:56
rikimaru2013, а mutable тебе чем не угодил? Он для этого как раз и сделан.
0
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
04.12.2015, 12:59  [ТС]
Цитата Сообщение от DrOffset Посмотреть сообщение
а mutable тебе чем не угодил? Он для этого как раз и сделан.
mutable const ? звучит как-то противоречаще.

В 46 строке же ж ошибка и только определенный класс в нужном namespace может делать магию - для других это обычный const
0
19491 / 10097 / 2460
Регистрация: 30.01.2014
Сообщений: 17,805
04.12.2015, 13:12
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
mutable const ? звучит как-то противоречаще.
Сам придумал - сам посмеялся?

Цитата Сообщение от rikimaru2013 Посмотреть сообщение
В 46 строке же ж ошибка и только определенный класс в нужном namespace может делать магию - для других это обычный const
Забавно, ты не понял, а объясняешь мне
Смотри:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
#include <iostream>
using namespace std;
 
template <typename T>
struct reinstallableconst;
 
class constchanger
{
public:
   template <typename T>
   static void change(reinstallableconst<T> const & obj, T const & newvalue )
   {
      obj.m_val = newvalue;
   }
};
 
template <typename T>
struct reinstallableconst
{
   reinstallableconst()
      : m_val()
   { }
   reinstallableconst(T const & constsetvalue )
      : m_val( constsetvalue )
   { }
 
   friend void constchanger::change<T>(reinstallableconst const &, T const &);
 
   T const & get() const
   {
       return m_val;
   }
 
private:
   mutable T m_val;
};
 
int main()
{
   reinstallableconst<int> speed( 199 );
 
   cout << speed.get() << endl;
   //speed.get() = 15;                                 // error: assign to a variable that is const
 
   constchanger::change<int>( speed, 51 );
   cout << speed.get() << endl;
}
Без хаков и UB.

А у тебя в коде как минимум 1 UB.
1) Нельзя писать в одно поле юниона, а читать из другого.

А вообще, за подобное трюкачество бывает скидывают с моста с забетонированными ногами. Лучше объясни что ты этим хочешь добиться?
1
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
04.12.2015, 13:25  [ТС]
Цитата Сообщение от DrOffset Посмотреть сообщение
А вообще, за подобное трюкачество бывает скидывают с моста с забетонированными ногами.
trust me, I am a engineer

Цитата Сообщение от DrOffset Посмотреть сообщение
Лучше объясни что ты этим хочешь добиться?
Ищу пути куда можно развиваться) Вот заинтересовался этим трюком - решил потестить.

Цитата Сообщение от DrOffset Посмотреть сообщение
А у тебя в коде как минимум 1 UB.
1) Нельзя писать в одно поле юниона, а читать из другого.
Так я думал в этом и смысл union - а насчёт UB хотел бы услышать объяснения - все биты валидные в union моём так как
C++
1
2
3
4
5
6
template <typename T>
union u
{
   T a;
   const T b;
};
Видел на github'e много кода
C++
1
2
3
4
5
union u
{
   std::int32_t a;
   std::int8_t[4] b;
};
Записали "пакеты" получили объект, или наоборот непомню. Но контекст тот.


Цитата Сообщение от DrOffset Посмотреть сообщение
Сам придумал - сам посмеялся?
Ну Вы сами написали это) Учитывая название темы модификатор cosnt должен быть у поля 100% ))))

Цитата Сообщение от DrOffset Посмотреть сообщение
Смотри
Инкапсуляция и классы - это же классика) Этот код бы неназывался в сети с приставкой "трюк", если можно было бы через геттеры/сеттеры.
0
19491 / 10097 / 2460
Регистрация: 30.01.2014
Сообщений: 17,805
04.12.2015, 13:36
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
Ну Вы сами написали это)
Я не писал это. В моей решении const может быть сам объект reinstallableconst и это не противоречит контракту, переносимо и обходится без UB.
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
Видел на github'e много кода
Это union cast. На подавляющем большиснвте реализаций работает, поэтому этим пользуются. Кроме того, в С++11 ввели понятие layout-compatible, что делает этот трюк безопасным для простых типов (удовлетворяющих условию совместимости). Однако того, что код "грязный" это не отменяет.

Цитата Сообщение от rikimaru2013 Посмотреть сообщение
все биты валидные
В стандарте 98/03 даже этот код был невалидный. В с++11 ввели понятие layout-compatible, что разрешило некоторые случаи использования. Но твой код все равно содержит UB по смежной причине:
9.2/19
Reading a volatile object through a non-volatile glvalue has undefined behavior
Кроме этого еще одно UB приходится на модификацию const.
7.1.6.1/4
Except that any class member declared mutable (7.1.1) can be modified, any attempt to modify a const object during its lifetime (3.8) results in undefined behavior.
В общем, бросай ты это.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
04.12.2015, 13:36
Помогаю со студенческими работами здесь

Конструктор внутри класса, поля которого являются членами другого класса
Вот фрагмент кода. class Class_Figure { Class_Triangle tr1; Class_Circle cr1; public: Class_Figure() { } void...

Использование в качестве поля класса указатель на объект другого класса
Ошибка в названии - &quot;указателЯ&quot; Вот, пытаюсь освоить ООП (пока только учусь): создаю класс person (человек) и car (модель машины). ...

Изменение статического закрытого элемента данных класса посредством статической элемент-функции класса
Добрый день. Не могу разобраться, как изменить закрытую статическую переменную класса. Вот код. Ошибка &quot;unresolved external&quot;. ...

Друзья, подскажите, говорят, что можно поля класса инициализировать в момент объявления класса. Как это сделать?
Скажу сразу, а то сейчас начнется, что я прекрасно понимаю, что поля класса при объявлении инициализировать нельзя. Можно конструктором при...

Создать событие на изменение поля класса
Доброго времени суток ! На днях разобрал такие темы как: Делегаты и События. Более менее разобрался. Вот сейчас хочу сделать пару...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
6
Ответ Создать тему
Новые блоги и статьи
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
Создание Single Page Application на фреймах
krapotkin 16.11.2025
Статья исключительно для начинающих. Подходы оригинальностью не блещут. В век Веб все очень привыкли к дизайну Single-Page-Application . Быстренько разберем подход "на фреймах". Мы делаем одну. . .
Фото: Daniel Greenwood
kumehtar 13.11.2025
Расскажи мне о Мире, бродяга
kumehtar 12.11.2025
— Расскажи мне о Мире, бродяга, Ты же видел моря и метели. Как сменялись короны и стяги, Как эпохи стрелою летели. - Этот мир — это крылья и горы, Снег и пламя, любовь и тревоги, И бескрайние. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru