powered by simpleCommunicator - 2.0.58     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / C++ [игнор отключен] [закрыт для гостей] / Почему
11 сообщений из 11, страница 1 из 1
Почему
    #39806833
semen.s.semen
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
#include <iostream>

struct T {
  T() { std::cout << "Constructor" << std::endl; }

  T(T &&t) noexcept { std::cout << "Move" << std::endl; }

  T(T &t) { std::cout << "Copy" << std::endl; }

  ~T() { std::cout << "Destructor" << std::endl; }
};

T getT1() {
  T ttt{};
  return ttt;
}

T getT() { return getT1(); }

int main() { T t = getT(); }



Запускаю и вижу
ВыводConstructor
Destructor


Почему не вызвались деструкторы промежуточных объектов ?

Всегда ли по стандарту вывод будет таким или это зависит от настроек ?
...
Рейтинг: 0 / 0
Почему
    #39806837
semen.s.semen
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Поставил

SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-elide-constructors")


Вывод:

Constructor
Move
Destructor
Move
Destructor
Move
Destructor
Move
Destructor
Destructor


))))

Весело
...
Рейтинг: 0 / 0
Почему
    #39806838
Dima T
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
У меня так пишет в DEBUG
Код: plaintext
1.
2.
3.
4.
Constructor
Move
Destructor
Destructor


и так в RELEASE
Код: plaintext
1.
2.
Constructor
Destructor



ИМХО скорее всего оптимизатор упростил код до такого
Код: plaintext
1.
int main() { T t; }
...
Рейтинг: 0 / 0
Почему
    #39806845
semen.s.semen
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Короче завязяваться на то что деструктор будет вызван ровно 1 раз не стоит
...
Рейтинг: 0 / 0
Почему
    #39806855
Dima T
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Чуть поправил класс
Код: plaintext
1.
2.
3.
4.
5.
6.
struct T {
	T() { std::cout << "Constructor" << this << std::endl; }
	T(T &&t) noexcept { std::cout << "Move" << this << std::endl; }
	T(T &t) { std::cout << "Copy" << this << std::endl; }
	~T() { std::cout << "Destructor" << this << std::endl; }
};


в дебаге выводит
Код: plaintext
1.
2.
3.
4.
Constructor000000000029F754
Move000000000029F9B4
Destructor000000000029F754
Destructor000000000029F9B4


т.е. в T(T &&t) происходит копирование.

Деструктор вызывается один раз для каждого объекта.
...
Рейтинг: 0 / 0
Почему
    #39806859
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
semen.s.semen
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
#include <iostream>

struct T {
  T() { std::cout << "Constructor" << std::endl; }

  T(T &&t) noexcept { std::cout << "Move" << std::endl; }

  T(T &t) { std::cout << "Copy" << std::endl; }

  ~T() { std::cout << "Destructor" << std::endl; }
};

T getT1() {
  T ttt{};
  return ttt;
}

T getT() { return getT1(); }

int main() { T t = getT(); }



Запускаю и вижу
ВыводConstructor
Destructor


Почему не вызвались деструкторы промежуточных объектов ?

Всегда ли по стандарту вывод будет таким или это зависит от настроек ?
RVO
В С++17 по моему уже принудительное
...
Рейтинг: 0 / 0
Почему
    #39806886
semen.s.semen
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Siemargl,

Его можно принудительно отключить
...
Рейтинг: 0 / 0
Почему
    #39807025
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
semen.s.semenSiemargl,

Его можно принудительно отключить
науха?

все равно вызовы парные
...
Рейтинг: 0 / 0
Почему
    #39807122
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
semen.s.semen,

Это RVO.
В зависимости от стандарта, поддерживаемого в текущем режиме компиляции, это может быть либо включаемой оптимизацией, либо гарантированным поведением.
Гарантированно оно кажется с 17 го стандарта.
Подробности на CPR
...
Рейтинг: 0 / 0
Почему
    #39807123
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
semen.s.semen,

Да, move constructor для этого не нужен, а
copy constructor должен (не для этого а просто по жизни)
Принимать const T&
...
Рейтинг: 0 / 0
Почему
    #39807124
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Dima TЧуть поправил класс
Код: plaintext
1.
2.
3.
4.
5.
6.
struct T {
	T() { std::cout << "Constructor" << this << std::endl; }
	T(T &&t) noexcept { std::cout << "Move" << this << std::endl; }
	T(T &t) { std::cout << "Copy" << this << std::endl; }
	~T() { std::cout << "Destructor" << this << std::endl; }
};


в дебаге выводит
Код: plaintext
1.
2.
3.
4.
Constructor000000000029F754
Move000000000029F9B4
Destructor000000000029F754
Destructor000000000029F9B4


т.е. в T(T &&t) происходит копирование.

Потому что ты move semantics не используешь, и оно тут не нужно

Деструктор вызывается один раз для каждого объекта.
...
Рейтинг: 0 / 0
11 сообщений из 11, страница 1 из 1
Форумы / C++ [игнор отключен] [закрыт для гостей] / Почему
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]