170 похожих чатов

Если у объекта вызвать деструктор, но при этом placement new

не вызывался, то это же UB? Типа:
Type t;
t.~Type();

37 ответов

7 просмотров

Можно пример кода?

На момент автоматического разрушения t, да.

Если ~T() нетривиален, то в #1 неопределенность: { T t; t.~T(); } /* #1 */

d7d1cd- Автор вопроса
Sergey Anisimov
Если ~T() нетривиален, то в #1 неопределенность: {...

Таак. То есть, сам вызов деструктора - не UB?

d7d1cd
Таак. То есть, сам вызов деструктора - не UB?

В #1 неопределенность, если ~T() - не псевдодеструктор (не от встроенного типа). Скорее всего для встроенных это можно. { T t; t.~T(); t.~T() /* #1 */; }

d7d1cd- Автор вопроса
Sergey Anisimov
В #1 неопределенность, если ~T() - не псевдодестру...

А если после вызова сделать вот так: Type t; t.~Type(); auto f = t.f; ?

d7d1cd- Автор вопроса
d7d1cd
Таак. То есть, сам вызов деструктора - не UB?

Вызывать деструктор можно, если есть гарантия, что он не будет вызван повторно при разрушении объекта. Примеры: placement new и union.

d7d1cd
А если после вызова сделать вот так: Type t; t.~Ty...

При попытке использовать этот объект будет обращение к указателям, по которым уже сделан delete. Ничего хорошего из этого не получится

d7d1cd
Указателям?

Ну если есть деструктор - внутри объекта есть какой-то ресурс. Никто не запрещает вызвать деструктор, а потом метод, который к этим ресурсом обращается. В частности, если там были указатели, то по ним был сделан delete и обращение к ним не сулит ничего хорошего

d7d1cd- Автор вопроса
Константин
Ну если есть деструктор - внутри объекта есть како...

Указатель внутри может не владеть ресурсом, а только "смотреть" на него.

Константин
Ну если есть деструктор - внутри объекта есть како...

> Никто не запрещает вызвать деструктор, а потом метод, который к этим ресурсом обращается. Запрещает: вызов деструктора завершает время жизни объекта. Все его идентификаторы (имена переменных, ссылки, указатели) прекращают называть его и называют область хранилища, в которой он располагался при жизни. Вызов нестатического метода через такой идентификатор составляет неопределенную операцию безотносительно состава его тела.

d7d1cd
Указатель внутри может не владеть ресурсом, а толь...

А ещё это мог быть деструктор по умолчанию, который вообще ничего не освобождает. В общем случае мы не знаем, что из этого будет

Aleksander Spichak
С если речь об implicit lifetime type?

Не имеет значения. "Мертвыми" объектами "типонасыщенно" пользоваться нельзя.

Sergey Anisimov
> Никто не запрещает вызвать деструктор, а потом м...

Я имел ввиду, что можно это написать и не будет ошибки компиляции. Понятное дело, что так делать не надо

компилятор имеет право отказать в компиляции, если докажет безусловное возникновение такой ситуации

Ну тот же malloc с 20 стандарта даёт нам сторэйж. И с ним можно работать как с любым из impl lifetime type. В чем подвох?

Aleksander Spichak
Ну тот же malloc с 20 стандарта даёт нам сторэйж. ...

Так это же про разное: impl-lifetime-type на то и таков, что время жизни начинается, хоть и неявно. В обсуждении выше же речь о доступе вне этого времени.

Aleksander Spichak
Ну тот же malloc с 20 стандарта даёт нам сторэйж. ...

в том, что этот storage выдан специальной implicit lifetime функцией

Ivan Sokolov
компилятор имеет право отказать в компиляции, если...

Это Warning у gcc. Скажет, что используется неинециализированная переменная. Но если это предупреждение проигнорировать - обращение к полям после вызова деструктора происходит успешно

Aleksander Spichak
Разве?

Some operations are described as implicitly creating objects within a specified region of storage. http://eel.is/c++draft/intro.object#10.sentence-1

Константин
Это Warning у gcc. Скажет, что используется неинец...

С самой памятью деструктор ведь ничего не делает

Константин
С самой памятью деструктор ведь ничего не делает

The properties ascribed to objects and references throughout this document apply for a given object or reference only during its lifetime. http://eel.is/c++draft/basic.life#4.sentence-1

Константин
С самой памятью деструктор ведь ничего не делает

это справедливо лишь для trivially destructible типов

Там более строгая формальность есть через 1, 2.

Sergey Anisimov
Там более строгая формальность есть через 1, 2.

да, но я решил, что это не добавит ясности ответу, а кратко уже не будет

d7d1cd- Автор вопроса

Отсюда читай

интересно, если напрямую вызвать деструктор, то при уничтожении объекта на стеке будет ли деструктор еще раз вызван

http://eel.is/c++draft/basic.life#9

Vlad
http://eel.is/c++draft/basic.life#9

ну вообще логично да

Похожие вопросы

Обсуждают сегодня

читать файл максимально быстро? странный вопрос))
zamtmn
53
всем привет! углубившись в плюсы и начав изучать реверсинг понял, что без асм'а никуда со своими высокоабстрактными представлениями начал изучать механизмы асма, и не совсем п...
9
Привет. Сразу скажу, что на C/C++/Rust я не пишу, но тем не менее возникла потребность дебага C/C++/Rust кода. Суть: есть серверное приложение, которое периодически ведёт себ...
ninekeem 🐳
4
буквально один оставшийся вопрос при выполнении строчки mov eax, 5 операнд "5" будет присутствовать где-либо в памяти (любой), кроме как в памяти блока .code? подвопрос: как...
12
Всем ку. Подскажите, если задекларировал массив так: int arr[10] = {1, 2, 3, 4}, то в arr[4] будет мусор или нуль?
Sasha K
14
я не понимаю mov [r11+8],rcx и прочие. мы записываем значение из rcx, куда?
Bor
15
а зачем этот вопрос для удаления из чата?
Mёdkinson Medvezhkin
63
у меня такой вопрос про память в x86 возник, может кто пояснить?.. у процессора есть (как минимум) 3 типа адресов (названия "п1", "п2", "п3" --- мои, чтобы проще было дальше)...
Toideng
5
А какие расширения активно используются в промышленности? Именно идейные, по типу гадт, а не всякие оверлоадедстрингс
Степан
11
у процессора есть (как минимум) 3 типа адресов (названия "п1", "п2", "п3" --- мои, чтобы проще было дальше): - "п1" --- виртуальный адрес, то есть тот, который ресолвится в "п...
Toideng
3
Карта сайта