Форум программистов, компьютерный форум, киберфорум
C++
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.64/11: Рейтинг темы: голосов - 11, средняя оценка - 4.64
1476 / 490 / 73
Регистрация: 22.09.2023
Сообщений: 1,505

Можно ли создать временную переменную для передачи значения в цепочке конструкторов?

09.09.2024, 12:47. Показов 2028. Ответов 3
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Есть у меня некий аппаратный буфер, от которого конструкторы базовых классов и членов "откусывают" себе необходимые кусочки. Сейчас это реализовано путем переменной в базовом классе, которую используют конструкторы классов-потомков и ссылки на которую передаются в конструкторы не связанных с этой иерархией классов. Конструктор из этой переменной получает смещение начала свободной части буфера, запоминает себе и увеличивает эту переменную на размер зарезервированной памяти.
Кликните здесь для просмотра всего текста
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
class base
{
protected:
    size_t Buffer_offset = 0;
};
 
class child : public base
{
    static size_t constexpr BUFFER_SIZE = 10;
public:
    child()
    : Buffer_offset(base::Buffer_offset)
    {
        base::Buffer_offset += BUFFER_SIZE;
    }
 
private:
    size_t Buffer_offset;
};
 
class other
{
    static size_t constexpr BUFFER_SIZE = 5;
public:
    other(size_t & buffer_offset)
    : Buffer_offset(buffer_offset)
    {
        buffer_offset += BUFFER_SIZE;
    }
 
private:
    size_t Buffer_offset;
};
 
class last : public child
{
public:
    last()
    : Other1(base::Buffer_offset)
    , Other2(base::Buffer_offset)
    {}
 
private:
    other   Other1;
    other   Other2;
}


Все работает. Но есть один нюанс, который не дает покоя моему чувству прекрасного: эта переменная после вызовов конструкторов больше не используется и только зря занимает место в ОЗУ. "Неаккуратненько!".

Вот отсюда и вопрос: есть ли элегантная (без километра шаблонов) возможность в конструкторе last перед вызовом остальных конструкторов создать временную автоматическую (без использования кучи) переменную, ссылку на которую я уже буду передавать в остальные конструкторы и которая будет автоматически уничтожена после выполнения конструктора last?
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
09.09.2024, 12:47
Ответы с готовыми решениями:

Поменять местами значения в переменных, не создавая временную третью переменную
Новичкам рассказывают об азах, показывают объявление переменных и т.п. А как практику дают задачу поменять местами значения переменных,...

Поменять местами значения двух целочисленных переменных не используя временную переменную
Задачка начального уровня.! Напишите программу которая меняет местами значения двух целочисленных переменных не используя временную...

Калькулятор: как создать переменную для промежуточного хранения значения?
Здравствуйте. Создал калькулятор на vba. Как создать переменную для промежуточного хранения значения? (расчете 2+2*4 выдает 8) Public...

3
112 / 110 / 30
Регистрация: 08.05.2021
Сообщений: 485
09.09.2024, 13:49
Лучший ответ Сообщение было отмечено Dushevny как решение

Решение

C++
1
last(size_t x = 0) :Other(x) {}
1
Вездепух
Эксперт CЭксперт С++
 Аватар для TheCalligrapher
13177 / 6813 / 1821
Регистрация: 18.10.2014
Сообщений: 17,237
09.09.2024, 22:37
Лучший ответ Сообщение было отмечено Dushevny как решение

Решение

Цитата Сообщение от Dushevny Посмотреть сообщение
Вот отсюда и вопрос: есть ли элегантная (без километра шаблонов) возможность в конструкторе last перед вызовом остальных конструкторов создать временную автоматическую (без использования кучи) переменную, ссылку на которую я уже буду передавать в остальные конструкторы и которая будет автоматически уничтожена после выполнения конструктора last?
Понятно, что для этого данную переменную придется передавать во все классы по ссылке, как вы делаете в other. Естественное решение: просто сделать конструкторы всех классов с параметром ссылкой

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
class child
{
    static size_t constexpr BUFFER_SIZE = 10;
public:
    child(size_t &offset) : Buffer_offset(offset)
    { 
      offset += BUFFER_SIZE; 
      std::cout << "child " << this << " " << Buffer_offset << std::endl;
    }
 
private:
    size_t Buffer_offset;
};
 
class other
{
    static size_t constexpr BUFFER_SIZE = 5;
public:
    other(size_t &offset) : Buffer_offset(offset)
    { 
      offset += BUFFER_SIZE; 
      std::cout << "other " << this << " " << Buffer_offset << std::endl;
    }
 
private:
    size_t Buffer_offset;
};
 
class last : public child
{
public:
    last(size_t &offset) : 
      child(offset),
      Other1(offset),
      Other2(offset)
    {
      std::cout << "last " << this << " final offset value " << offset << std::endl;
    }
 
private:
    other   Other1;
    other   Other2;
};
а задачу предоставления lvalue с правльным начальным значением взвалить на вызывающий код. Если вызывающий код локален, то все просто - запросто получается локальная переменная, как вы и хотели

C++
1
2
3
4
5
int main()
{
  size_t offset = 0;
  last l_local(offset);
}
А вот чтобы проинициализировать класс в глобальном котнтексте, придется что-то изобретать. Например

C++
1
2
3
4
5
6
7
struct lvalue_temp_offset 
{ 
  size_t offset = 0;
  operator size_t &() { return offset; }
};
 
last l_global(lvalue_temp_offset{});
Разумеется, никто вам не запрещает передавать инициализатор lvalue_temp_offset{} и при локальных объявлениях.

https://coliru.stacked-crooked... c2906fb58a

Ну и, если вы сильно хотите, чтобы класс верхнего уровня можно было конструировать конструктором по умолчанию, lvalue_temp_offset{} можно указать в качестве аргумента по умолчанию в конструкторе класса верхнего уровня.
1
1476 / 490 / 73
Регистрация: 22.09.2023
Сообщений: 1,505
11.09.2024, 09:31  [ТС]
Цитата Сообщение от TheCalligrapher Посмотреть сообщение
Ну и, если вы сильно хотите, чтобы класс верхнего уровня можно было конструировать конструктором по умолчанию, lvalue_temp_offset{} можно указать в качестве аргумента по умолчанию в конструкторе класса верхнего уровня.
Да, тоже пришел к такому решению после ответа mashmed135. Тут еще хорошо, что это отдельный класс и вместо него случайно не подставишь число (иногда приходят в голову светлые мысли и аргументы конструктора верхнего класса приходится менять. Стараюсь делать так, чтобы использующий эту библиотеку старый код в таком случае вызывал ошибку компиляции).
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
11.09.2024, 09:31
Помогаю со студенческими работами здесь

Можно ли создать в C++ ограниченную переменную (для экономии памяти) без использования классов
Например, переменную, скажем, test, которая принимает значение в диапазоне (-180..+180)

Задать временную переменную
Здравствуйте! Пожалуйста, покажите код VBA вот этого макроса! Заранее благодарен!

Оптимизированные для памяти таблицы. Моно ли создать такую временную (# или ##)
Приветствую! Можно ли создать временные таблицы обоих типов, как оптимизированные для памяти? Хотелось бы узнать ДО создания отдельной...

Как вытащить из Return в переменную для передачи в форму?
У меня такая проблема. Мне нужно вытащить именно те данные, которые выводить return. Пробовал вместо return записать в переменную, а...

Создать триггер для занесения стоимости каждого проданного билета во временную таблицу
Если кто-нибyдь может, то помогите пожалyйста. Все задания сделал, кроме этого, просто с триггерами как то не заладилось Создать...


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

Или воспользуйтесь поиском по форуму:
4
Ответ Создать тему
Новые блоги и статьи
SDL3 для Desktop (MinGW): Рисуем цветные прямоугольники с помощью рисовальщика SDL3 на Си и C++
8Observer8 17.03.2026
Содержание блога Финальные проекты на Си и на C++: finish-rectangles-sdl3-c. zip finish-rectangles-sdl3-cpp. zip
Символические и жёсткие ссылки в Linux.
algri14 15.03.2026
Существует два типа ссылок — символические и жёсткие. Ссылка в Linux — это запись в каталоге, которая может указывать либо на inode «файла-ИСТОЧНИКА», тогда это будет «жёсткая ссылка» (hard link),. . .
[Owen Logic] Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора
ФедосеевПавел 14.03.2026
Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора ВВЕДЕНИЕ Выполняя задание на управление насосной группой заполнения резервуара,. . .
делаю науч статью по влиянию грибов на сукцессию
anaschu 13.03.2026
прикрепляю статью
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога Финальные проекты на Си и на C++: hello-sdl3-c. zip hello-sdl3-cpp. zip Результат:
Установка CMake и MinGW 13.1 для сборки С и C++ приложений из консоли и из Qt Creator в EXE
8Observer8 10.03.2026
Содержание блога MinGW - это коллекция инструментов для сборки приложений в EXE. CMake - это система сборки приложений. Здесь описаны базовые шаги для старта программирования с помощью CMake и. . .
Как дизайн сайта влияет на конверсию: 7 решений, которые реально повышают заявки
Neotwalker 08.03.2026
Многие до сих пор воспринимают дизайн сайта как “красивую оболочку”. На практике всё иначе: дизайн напрямую влияет на то, оставит человек заявку или уйдёт через несколько секунд. Даже если у вас. . .
Модульная разработка через nuget packages
DevAlt 07.03.2026
Сложившийся в . Net-среде способ разработки чаще всего предполагает монорепозиторий в котором находятся все исходники. При создании нового решения, мы просто добавляем нужные проекты и имеем. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru