Здравствуйте, Аноним, Вы писали:
А>Помогите новичку! А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
когда конструктор не отработал до конца т.е. вылетело исключение — деструкторы вызываются только для полностью созданных объектов.
Здравствуйте, Аноним, Вы писали:
А>Помогите новичку! А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
1. Когда бросается исключение, которое нигде не ловится.
2. (MSVC specific) при возникновении SEH исключений в приложении, в котором один из модулей (бросающий или перехватывающий это исключение) скомпилирован с выключенной опцией /EHa
--
Справедливость выше закона. А человечность выше справедливости.
Здравствуйте, Аноним, Вы писали:
А>Помогите новичку! А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
А в связи с чем вопрос?
Ну, там
— на собеседовании спросили
— обнаружен баг
— обнаружено странное поведение
— нужно добиться такого поведения
и т.д.
А то можно всякого навыдумывать.
Любое завершение потока или процесса, не сопровождающееся раскруткой стека. То есть, terminate(), abort(), exit(), ExitThread(), TerminateThread(), SEH, signal...
Любой прыжок в коде. longjmp(), повреждение стека, указателя на функцию, указателя на таблицу виртуальных функций, с последующим переходом в чёрт знает куда.
Потеря информации о типе. delete (NonvirtualBase*) new Derived(), повреждение указателя на таблицу виртуальных функций (например, вместо присваивания сделали memcpy базового класса — подменили vfptr наследника на базовый).
Нарушение защиты памяти, повреждение секций кода или констант (таблицы виртуальных функций).
И прочая, и прочая, и прочая.
Здравствуйте, vitcpp, Вы писали:
А>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
V>Классический пример — отсутствие виртуального деструктора — http://cpp-reference.ru/articles/virtual-destructor/
В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
Здравствуйте, rg45, Вы писали:
R>Здравствуйте, Nikita.Trophimov, Вы писали:
R>>>1. Когда бросается исключение, которое нигде не ловится.
NT>>Это unspecified.
R>Вопрос был, "когда может...". А в этом случае может.
A>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>это же чушь. A>где Вы нашли этот говносайт?
А что тут не так ?
Вроде как удаление через указатель на базовый с невиртуальным деструктором = UB (по стандарту 2003, а как по новому интересно ?)
Здравствуйте, Abyx, Вы писали:
R>>>>1. Когда бросается исключение, которое нигде не ловится.
NT>>>Это unspecified.
R>>Вопрос был, "когда может...". А в этом случае может.
A>в нормальных компиляторах не может.
К сожалению, ТС ничего не сообщил о степени нормальности своего компилятора. Кроме того, раз стандарт допускает такое поведение, значит оно может иметь место в любых компиляторах.
--
Справедливость выше закона. А человечность выше справедливости.
A>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>>это же чушь. A>>где Вы нашли этот говносайт?
sts>А что тут не так ?
деструктор полиморфного базового класса может быть каким угодно.
sts>Вроде как удаление через указатель на базовый с невиртуальным деструктором = UB (по стандарту 2003, а как по новому интересно ?)
вызов delete — UB, но это же не единственный способ разрушить объект
A>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>это же чушь. A>где Вы нашли этот говносайт?
Почему чушь? Обоснуйте.
A>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>это же чушь.
Это высказывание является прямым следствием из 5.3.5/3.
A>где Вы нашли этот говносайт?
А с сайтом что не так?
--
Справедливость выше закона. А человечность выше справедливости.
A>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>>это же чушь.
R>Это высказывание является прямым следствием из 5.3.5/3.
это не может быть следствием, т.к. `delete pointer-to-base-type;` это не единственный способ корректно разрушить объект через указатель на его базовый класс.
R>А с сайтом что не так?
то что на нем такие статьи
Это все понятно. Полагаю, вы слишком формально подходите к статье, и вас смутило слово "должен". Но по сути, описано хорошее правило делать деструктор виртуальным в случае полиморфных типов. Можно использовать обычный деструктор, если вы точно уверены, как именно ваша иерархия классов будет использоваться или в целях оптимизации.
A>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>>это же чушь.
R>Это высказывание является прямым следствием из 5.3.5/3.
struct A { virtual f(); ~A(); };
struct B:A { f(); };
int main()
{
B b;
A* pa = &b;
pa->f(); //полиморфный!
}
Здесь В замечательно обходится без виртуального деструктора и все корректно уничтожается, а 5.3.5/3 идет по градиенту.
А>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
V>Классический пример — отсутствие виртуального деструктора — http://cpp-reference.ru/articles/virtual-destructor/
В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
Технически никому он ничего не должен, особенно если:
1. он protected
2. delete вызывается не на Base*, хотя хранится именно Base* (например deleter в shared_ptr знающий правильный тип, хотя хранится Base*)
3. как показано выше — объект может быть локальным
Но, ссылка выше это же rule of thumb для новичков?
Здравствуйте, jazzer, Вы писали:
J>int main() J>{ J> B b; J> A* pa = &b; pa->>f(); //полиморфный! J>} J>[/ccode] J>Здесь В замечательно обходится без виртуального деструктора и все корректно уничтожается, а 5.3.5/3 идет по градиенту.
разрушение объекта производного класса через указатель на соответствующий базовый класс
Здравствуйте, Evgeny.Panasyuk, Вы писали:
А>>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
V>>Классический пример — отсутствие виртуального деструктора — http://cpp-reference.ru/articles/virtual-destructor/
EP>
EP>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
EP>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
EP>Технически никому он ничего не должен, особенно если: EP>1. он protected
тогда не получится "удалять через указатель на базовый класс" EP>2. delete вызывается не на Base*, хотя хранится именно Base* (например deleter в shared_ptr знающий правильный тип, хотя хранится Base*)
там нет "удаления через указатель на базовый класс" — сначала указателю делается статик-каст к фактическому типу EP>3. как показано выше — объект может быть локальным
там тоже нет "удаления через указатель на базовый класс"
EP>Но, ссылка выше это же rule of thumb для новичков?
это да
но и пятница же
Здравствуйте, sts, Вы писали:
sts>тогда не получится "удалять через указатель на базовый класс"
sts>там нет "удаления через указатель на базовый класс" — сначала указателю делается статик-каст к фактическому типу
sts>там тоже нет "удаления через указатель на базовый класс"
это же ответ на:
В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
которое стоит самым первым предложением.
По аналогии можно сказать:
На планете Земля, все люди должны носить шлем. Только так обеспечивается защита головы при падениях с мотоцикла.
EP>>Но, ссылка выше это же rule of thumb для новичков? sts>это да sts>но и пятница же
Здравствуйте, Аноним, Вы писали:
А>Помогите новичку! А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
Удаление неполного класса — одни из самых неприятных плюсовых граблей.
Тоже деструктор pImpl не будет вызван.
Лечится через unique_ptr (который не даст удалить неполный тип) и добавление ~Owner() туда, где Impl уже определен.
Здравствуйте, jazzer, Вы писали:
J>Здравствуйте, rg45, Вы писали:
A>>>
A>>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>>>это же чушь.
R>>Это высказывание является прямым следствием из 5.3.5/3.
J>
J>struct A { virtual f(); ~A(); };
J>struct B:A { f(); };
J>int main()
J>{
J> B b;
J> A* pa = &b;
pa->>f(); //полиморфный!
J>}
J>
J>Здесь В замечательно обходится без виртуального деструктора и все корректно уничтожается, а 5.3.5/3 идет по градиенту.
Где в этом примере (цитирую) "разрушение объекта производного класса через указатель на соответствующий базовый класс" о котором шла речь выше?
Да, к сожалению, авторы статьи не дали четкого определения, что они понимают под полиморфным классом. Из общего контекста статьи можно догадаться, что они вкладывали в это понятие более широкий смысл — класс, объекты которого могут не только использоваться, но и удаляться через указатель базового класса (именно этому вопросу в статье уделено много внимания). Конечно же, это недочет, неточность формулировки, но еще не повод разбрасываться ярлыками типа "чушь" и "говносайт".
--
Справедливость выше закона. А человечность выше справедливости.
V>Это все понятно. Полагаю, вы слишком формально подходите к статье, и вас смутило слово 'должен'. Но по сути, описано хорошее правило делать деструктор виртуальным в случае полиморфных типов. Можно использовать обычный деструктор, если вы точно уверены, как именно ваша иерархия классов будет использоваться или в целях оптимизации.
хорошее правило — это 'не делать того что не нужно делать' или 'делать только то что нужно делать'.
если виртуальный деструктор не нужен, то незачем его делать.
Здравствуйте, Abyx, Вы писали:
A>это не может быть следствием, т.к. `delete pointer-to-base-type;` это не единственный способ корректно разрушить объект через указатель на его базовый класс.
Вероятно, ты имеешь ввиду технику, подобную той, которая применяется в shared_ptr? Ну так в ней разрушение объекта производится как раз через указатель most derived класса (при правильно использовании, при неправильном можно получить все то же UB). При этом сам shared_ptr я бы рассматривал не как способ разрушения объекта, а как средство абстрагирования от деталей этого процесса.
Или ты что-то другое имеешь в виду? Ну тогда поделись, как еще можно разрушить объект через указатель на его базовый класс.
--
Справедливость выше закона. А человечность выше справедливости.
Здравствуйте, rg45, Вы писали:
A>>это не может быть следствием, т.к. `delete pointer-to-base-type;` это не единственный способ корректно разрушить объект через указатель на его базовый класс.
R>Вероятно, ты имеешь ввиду технику, подобную той, которая применяется в shared_ptr? Ну так в ней разрушение объекта производится как раз через указатель most derived класса (при правильно использовании, при неправильном можно получить все то же UB). При этом сам shared_ptr я бы рассматривал не как способ разрушения объекта, а как средство абстрагирования от деталей этого процесса.
R>Или ты что-то другое имеешь в виду? Ну тогда поделись, как еще можно разрушить объект через указатель на его базовый класс.
да, удалять объект можно с помощью deleter'а с type-erasure как у shared_ptr,
причем *внезапно* shared_ptr<BaseClass> это *указатель* на базовый класс.
еще объект может владеть сам собой (встроенный счетчик ссылок и delete this, как например в COM),
объект может удалять какой-то GC (напр. Arena GC), впрочем это опять же deleter.
A>>>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
R>Да, к сожалению, авторы статьи не дали четкого определения, что они понимают под полиморфным классом. Из общего контекста статьи можно догадаться, что они вкладывали в это понятие более широкий смысл — класс, объекты которого могут не только использоваться, но и удаляться через указатель базового класса (именно этому вопросу в статье уделено много внимания). Конечно же, это недочет, неточность формулировки, но еще не повод разбрасываться ярлыками типа "чушь" и "говносайт".
вот поэтому статья и говно, раз там написана чушь наподобие "раз полиморфный — значит ДОЛЖЕН быть виртуальный деструктор".
про весь сайт я может погорячился, хотя раз там есть статья такого качества — наверное и весь сайт такой.
у термина "полиморфный (класс)" есть вполне конкретное определение.
то что на это определение наложено ограничение, что объекты потомков такого класса будут удаляться через delete — это называется "более узкий смысл".
EP>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
EP>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
EP>>Технически никому он ничего не должен, особенно если: EP>>1. он protected sts>тогда не получится "удалять через указатель на базовый класс"
не подменяйте тему.
в цитате написано не "удалять", а разрушать.
это разные вещи.
Здравствуйте, sts, Вы писали:
sts>Удаление неполного класса — одни из самых неприятных плюсовых граблей. sts>Тоже деструктор pImpl не будет вызван. sts>Лечится через unique_ptr (который не даст удалить неполный тип) и добавление ~Owner() туда, где Impl уже определен.
лечится включением предупреждений в компиляторе.
In Zen We Trust
Re: Разрушение компа прежде, чем будет разрушен объект, покатит? ;)
Здравствуйте, Аноним, Вы писали:
А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
на пример, если объёкт создали на компе, установленном на борут ГЧ, достигшей цели
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Здравствуйте, Abyx, Вы писали:
A>>>это не может быть следствием, т.к. `delete pointer-to-base-type;` это не единственный способ корректно разрушить объект через указатель на его базовый класс.
R>>Вероятно, ты имеешь ввиду технику, подобную той, которая применяется в shared_ptr? Ну так в ней разрушение объекта производится как раз через указатель most derived класса (при правильно использовании, при неправильном можно получить все то же UB). При этом сам shared_ptr я бы рассматривал не как способ разрушения объекта, а как средство абстрагирования от деталей этого процесса.
R>>Или ты что-то другое имеешь в виду? Ну тогда поделись, как еще можно разрушить объект через указатель на его базовый класс.
A>да, удалять объект можно с помощью deleter'а с type-erasure как у shared_ptr, A>причем *внезапно* shared_ptr<BaseClass> это *указатель* на базовый класс.
A>еще объект может владеть сам собой (встроенный счетчик ссылок и delete this, как например в COM), A>объект может удалять какой-то GC (напр. Arena GC), впрочем это опять же deleter.
A>много в общем разных способов.
Я понимаю, о чем ты говоришь, более того, сам придерживаюсь примерно тех же взглядов, и уже писал ранее по данной теме: http://rsdn.ru/forum/cpp/4071405.1
. Как мне кажется, при изучении C++ вообще, и особенно таких вопросов как времени жизни объектов и владение, прежде чем приступать к вопросам дизайна и паттернам проектирования, нужно познакомиться с синтаксисом и базовыми концепциями C++ на несколько более низком уровне. Название сайта "C++ reference" несколько ввело меня в заблуждение — я подумал, что его авторы как раз и поставили перед собой задачу познакомить читателя с основами языка, поэтому и не удивился, что они достаточно узко рассматривают вопросы удаления объектов, не рассматривая других аспектов и возможных реализаций владения. Хотя, могли бы, с учетом того, что паттернам они таки уделяют некоторое внимание.
--
Справедливость выше закона. А человечность выше справедливости.
Здравствуйте, rg45, Вы писали:
R>Здравствуйте, jazzer, Вы писали:
J>>Здравствуйте, rg45, Вы писали:
A>>>>
A>>>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
A>>>>это же чушь.
R>>>Это высказывание является прямым следствием из 5.3.5/3.
J>>
J>>struct A { virtual f(); ~A(); };
J>>struct B:A { f(); };
J>>int main()
J>>{
J>> B b;
J>> A* pa = &b;
pa->>>f(); //полиморфный!
J>>}
J>>
J>>Здесь В замечательно обходится без виртуального деструктора и все корректно уничтожается, а 5.3.5/3 идет по градиенту.
R>Где в этом примере (цитирую) "разрушение объекта производного класса через указатель на соответствующий базовый класс" о котором шла речь выше?
Нету, в том-то и дело. Полиморфное использование есть, а полиморфного удаления нету.
R>Да, к сожалению, авторы статьи не дали четкого определения, что они понимают под полиморфным классом. Из общего контекста статьи можно догадаться, что они вкладывали в это понятие более широкий смысл — класс, объекты которого могут не только использоваться, но и удаляться через указатель базового класса (именно этому вопросу в статье уделено много внимания). Конечно же, это недочет, неточность формулировки, но еще не повод разбрасываться ярлыками типа "чушь" и "говносайт".
Ну, я конкретно не разбрасывался, но заявления типа "В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным." и "Cуществует правило — если базовый класс предназначен для полиморфного использования, то его деструктор должен объявляться виртуальным." являются слишком смелым обобщением, годным разве что для совсем начинающих, чтоб не отстрелили себе что-нть.
Правильная формулировка была бы такой: "если базовый класс предназначен для полиморфного использования удаления, то его деструктор должен объявляться виртуальным. Т.е. если ты не собираешься удалять объекты по голому указателю на базовый класс — нет необходимости делать деструктор виртуальным.
Например, есть у тебя std::map< std::string, std::shared_ptr<А> > — так вот в такую мапу ты вполне можешь запихивать указатели на В, и все будет правильно удаляться безо всяких виртуальных деструкторов (есть такое свойство у shared_ptr — deleter внутри него инициализируется в самом начале, и поэтому он знает, какой класс надо удалять).
Здравствуйте, Abyx, Вы писали:
A>Здравствуйте, sts, Вы писали:
sts>>Удаление неполного класса — одни из самых неприятных плюсовых граблей. sts>>Тоже деструктор pImpl не будет вызван. sts>>Лечится через unique_ptr (который не даст удалить неполный тип) и добавление ~Owner() туда, где Impl уже определен.
A>лечится включением предупреждений в компиляторе.
что лечится ?
если включить предупреждения, то деструктор вызовется ?
не верю
Re[2]: Разрушение компа прежде, чем будет разрушен объект, покатит? ;)
Здравствуйте, Erop, Вы писали:
E>Здравствуйте, Аноним, Вы писали:
А>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
E>на пример, если объёкт создали на компе, установленном на борут ГЧ, достигшей цели
так ведь и delete не успели сделатьт, так что это не в счет
Re[3]: Разрушение компа прежде, чем будет разрушен объект, покатит? ;)
Здравствуйте, sts, Вы писали:
А>>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
E>>на пример, если объёкт создали на компе, установленном на борут ГЧ, достигшей цели
sts>так ведь и delete не успели сделатьт, так что это не в счет
Ты ТС или просто рассуждаешь?
Я так понял, что ТС спросил, когда может так получится, что у созхданного С++ объекта не будет вызван деструктор. при этом случай с забытым delete, он считал тривиальным и просил на него не отвлекаться. на этот вопрос я и ответил...
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[4]: Разрушение компа прежде, чем будет разрушен объект, покатит? ;)
Здравствуйте, Erop, Вы писали:
E>Здравствуйте, sts, Вы писали:
А>>>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
E>>>на пример, если объёкт создали на компе, установленном на борут ГЧ, достигшей цели
sts>>так ведь и delete не успели сделатьт, так что это не в счет E>Ты ТС или просто рассуждаешь? E>Я так понял, что ТС спросил, когда может так получится, что у созхданного С++ объекта не будет вызван деструктор. при этом случай с забытым delete, он считал тривиальным и просил на него не отвлекаться. на этот вопрос я и ответил...
брутально, можно было никого не взрывать, а просто комп из розетки выдернуть
Здравствуйте, Abyx, Вы писали:
A>Здравствуйте, sts, Вы писали:
EP>>>
EP>>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
EP>>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
EP>>>Технически никому он ничего не должен, особенно если: EP>>>1. он protected sts>>тогда не получится "удалять через указатель на базовый класс"
A>не подменяйте тему. A>в цитате написано не "удалять", а разрушать. A>это разные вещи.
V>>Это все понятно. Полагаю, вы слишком формально подходите к статье, и вас смутило слово 'должен'. Но по сути, описано хорошее правило делать деструктор виртуальным в случае полиморфных типов. Можно использовать обычный деструктор, если вы точно уверены, как именно ваша иерархия классов будет использоваться или в целях оптимизации.
A>хорошее правило — это 'не делать того что не нужно делать' или 'делать только то что нужно делать'. A>если виртуальный деструктор не нужен, то незачем его делать.
в данном случае это надо делать (делать деструктор виртуальным), т.к. большинство разработчиков этого ожидают
Здравствуйте, Abyx, Вы писали:
A>Здравствуйте, rg45, Вы писали:
A>>>это не может быть следствием, т.к. `delete pointer-to-base-type;` это не единственный способ корректно разрушить объект через указатель на его базовый класс.
R>>Вероятно, ты имеешь ввиду технику, подобную той, которая применяется в shared_ptr? Ну так в ней разрушение объекта производится как раз через указатель most derived класса (при правильно использовании, при неправильном можно получить все то же UB). При этом сам shared_ptr я бы рассматривал не как способ разрушения объекта, а как средство абстрагирования от деталей этого процесса.
R>>Или ты что-то другое имеешь в виду? Ну тогда поделись, как еще можно разрушить объект через указатель на его базовый класс.
A>да, удалять объект можно с помощью deleter'а с type-erasure как у shared_ptr, A>причем *внезапно* shared_ptr<BaseClass> это *указатель* на базовый класс.
A>еще объект может владеть сам собой (встроенный счетчик ссылок и delete this, как например в COM), A>объект может удалять какой-то GC (напр. Arena GC), впрочем это опять же deleter.
A>много в общем разных способов.
нету в shared_ptr удаления через указатель на базовый класс — там базовый класс кастуется к нужному прежде чем удалить
Здравствуйте, Abyx, Вы писали:
A>Здравствуйте, rg45, Вы писали:
A>>>>>
A>>>>>В языке программирования C++ деструктор полиморфного базового класса должен объявляться виртуальным.
A>>>>>Только так обеспечивается корректное разрушение объекта производного класса через указатель на соответствующий базовый класс.
R>>Да, к сожалению, авторы статьи не дали четкого определения, что они понимают под полиморфным классом. Из общего контекста статьи можно догадаться, что они вкладывали в это понятие более широкий смысл — класс, объекты которого могут не только использоваться, но и удаляться через указатель базового класса (именно этому вопросу в статье уделено много внимания). Конечно же, это недочет, неточность формулировки, но еще не повод разбрасываться ярлыками типа "чушь" и "говносайт".
A>вот поэтому статья и говно, раз там написана чушь наподобие "раз полиморфный — значит ДОЛЖЕН быть виртуальный деструктор". A>про весь сайт я может погорячился, хотя раз там есть статья такого качества — наверное и весь сайт такой.
A>у термина "полиморфный (класс)" есть вполне конкретное определение. A>то что на это определение наложено ограничение, что объекты потомков такого класса будут удаляться через delete — это называется "более узкий смысл".
ожидается, что деструктор будет полиморфным
так же как ожидается, что из него не будет выкинуто исключение
Здравствуйте, Аноним, Вы писали:
А>Помогите новичку! А>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
Деструкторы могут не вызываться при создании массива с помощью оператора new[] и удалении его(массива) с помощью оператора delete.
Пример:
class A
{
public:
~A(){}
};
int main()
{
A* a = new A[100500];
...
delete a; // should be delete[] a;
}
Здравствуйте, sts, Вы писали:
V>>>Это все понятно. Полагаю, вы слишком формально подходите к статье, и вас смутило слово 'должен'. Но по сути, описано хорошее правило делать деструктор виртуальным в случае полиморфных типов. Можно использовать обычный деструктор, если вы точно уверены, как именно ваша иерархия классов будет использоваться или в целях оптимизации.
A>>хорошее правило — это 'не делать того что не нужно делать' или 'делать только то что нужно делать'. A>>если виртуальный деструктор не нужен, то незачем его делать.
sts>в данном случае это надо делать (делать деструктор виртуальным), т.к. большинство разработчиков этого ожидают
большинство разработчиков (С++) не знают С++, не знают стандартную библиотеку и называет шаблоны магией, ну и что?
не надо равняться на таких людей.
Здравствуйте, sts, Вы писали:
A>>у термина "полиморфный (класс)" есть вполне конкретное определение. A>>то что на это определение наложено ограничение, что объекты потомков такого класса будут удаляться через delete — это называется "более узкий смысл".
sts>ожидается, что деструктор будет полиморфным sts>так же как ожидается, что из него не будет выкинуто исключение
*тобой* ожидается? да кого это волнует
In Zen We Trust
Re[5]: Разрушение компа прежде, чем будет разрушен объект, покатит? ;)
Здравствуйте, sts, Вы писали:
sts>брутально, можно было никого не взрывать, а просто комп из розетки выдернуть
Это какой-то форс-мажор, на который не понятно, надо ли рассчитывать вообще при проектировании ПО для этого компа.
А вот на то, что ГЧ поразит таки цель, авторам её ПО рассчитывать стоит...
Впрочем, если тебя пугает брутальность, есть более мягкий вариант. Кроме БЧ есть много других устройств, в которых останов ПО не предусмотрен. То есть раз запущенное оно крутится на устройстве до конца его функционирования, либо до аппаратного сбоя/холодного рестарта. Там вызов дестукторов статических объектов обычно тоже не прежусмотрен,..
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Здравствуйте, Abyx, Вы писали:
sts>>ожидается, что деструктор будет полиморфным sts>>так же как ожидается, что из него не будет выкинуто исключение
A>*тобой* ожидается? да кого это волнует
А какой профит делать публичный невиртуальный деструктор если vtbl уже есть в классе?
Я могу представить пару очень особенных случаев, но даже про них не уверен что оно того стоит.
Здравствуйте, doarn, Вы писали:
D>Здравствуйте, Abyx, Вы писали:
sts>>>ожидается, что деструктор будет полиморфным sts>>>так же как ожидается, что из него не будет выкинуто исключение
A>>*тобой* ожидается? да кого это волнует
D>А какой профит делать публичный невиртуальный деструктор если vtbl уже есть в классе? D>Я могу представить пару очень особенных случаев, но даже про них не уверен что оно того стоит.
про "публичный" никто не говорил.
впрочем про то что его надо "делать" — тоже
Здравствуйте, Фаллопиева труба, Вы писали:
А>>Помогите новичку! А>>Какие могут быть ситуации, когда не вызывается дестуктор(сделал new и не сделал delete не в счет)?
ФТ>Деструкторы могут не вызываться при создании массива с помощью оператора new[] и удалении его(массива) с помощью оператора delete.
Это называется "сделал new[] и не сделал delete[]"
Не считая того, что new[]/delete — это UB. (И одним из возможных эффектов этого поведения будет невызов деструкторов).
И кстати, мы говорим про new[] expression или про operator new[] ?