Re[2]: default constructor
От: Denwer Россия  
Дата: 20.05.04 10:42
Оценка:
Здравствуйте, Fox, Вы писали:

Fox>Здравствуйте, kvas, Вы писали:


K>>Есть код:



K>>
K>>#include <iostream>

K>>struct Foo
K>>{
K>>    //Foo() {};
K>>    ~Foo() { std::cout << "Destructor was called" << std::endl; }
K>>};

K>>void main()
K>>{
K>>    Foo &r = Foo();
K>>}
K>>


K>>Исполнение этого кода, скомпилированного VC 7.1, приводит к выводу двух строк "Destructor was called".

K>>А если раскомментировать явное определение default constructor, то одной строки.
K>>Почему так?

Fox>Хотите еще веселее ???

Fox>Попробуйте деструктор сделать виртуальным
Fox>Будет один раз срабатывать.

Ну если бы он еще и при виртуальном деструкторе копию создавал, тогда бы вообще повеситься можно.
Re: default constructor
От: Fox Россия  
Дата: 20.05.04 10:44
Оценка:
да и еще вовсе необязательно делать так
Foo &r = Foo();

можно просто:

Foo r = Foo();
Re[2]: default constructor
От: just_bear Россия  
Дата: 20.05.04 10:51
Оценка:
Здравствуйте, Fox, Вы писали:

Fox>да и еще вовсе необязательно делать так

Fox>Foo &r = Foo();

Fox>можно просто:


Fox>Foo r = Foo();


Ну тогда уж

Foo r;
Re: default constructor
От: Кодт Россия  
Дата: 20.05.04 10:54
Оценка:
Здравствуйте, kvas, Вы писали:

K>Исполнение этого кода, скомпилированного VC 7.1, приводит к выводу двух строк "Destructor was called".

K>А если раскомментировать явное определение default constructor, то одной строки.
K>Почему так?

Достаточно выводить адрес объекта, чтобы понять картину.

В первом случае создаётся и убивается временный объект, а объект по ссылке (кстати, можно и без ссылки, а просто!)
 Foo f = Foo();

создаётся конструктором копирования и убивается по выходу из блока.

Во втором случае — обходятся без промежуточного объекта.



Инициализация присваиванием может проходить по двум сценариям: конструирование как есть и копирование.
Оба варианта равноправны и отдаются компилятору.

Вообще же, если класс CopyConstructible и Assignable, то побочные эффекты (здесь — вывод в консоль) в конструкторах, деструкторе и присваивании лучше не делать. Потому что иначе получается unspecified / implementation-defined behaviour, то есть — как повезёт.
Перекуём баги на фичи!
Re[2]: default constructor
От: UGN  
Дата: 20.05.04 11:06
Оценка:
Здравствуйте, Кодт, Вы писали:

К>Вообще же, если класс CopyConstructible и Assignable, то побочные эффекты (здесь — вывод в консоль) в конструкторах, деструкторе и присваивании лучше не делать. Потому что иначе получается unspecified / implementation-defined behaviour, то есть — как повезёт.


Это вывод из отдельных положений стандарта или там есть отдельный пункт с таким утверждением?

И что еще считать побочным эффектом?
Re[6]: default constructor
От: jazzer Россия Skype: enerjazzer
Дата: 20.05.04 11:26
Оценка:
Здравствуйте, Mr. None, Вы писали:

MN>Здравствуйте, jazzer, Вы писали:


MN>>>Нет никакого глюка.


MN>>>В первом случае создаётся ещё один временный объект — вот и 2 вызова деструктора: 1-ый для Foo() (вызывается когда завершается инициализация ссылки), 2-ой для временного объекта созданного компилятором и связанного с сылкой (вызывается когда уничтожается ссылка).

MN>>>Во втором случае компилятор непосредственно связывает временный объект, созданный вызовом Foo() с сылкой и удерживает его до уничтожения ссылки — деструктор вызывается один раз.

MN>>>По стандарту компилятор может поступать и так и эдак, причём делает это он на своё усмотрение.


J>>А можно ссылочку?

J>>Что-то я не помню разрешения плодить временные объекты

MN>Стандарт — 8.5.3/4, 12.2/1, 12.2/5 ;)


Угу, уже нашел :)
jazzer (Skype: enerjazzer) Ночная тема для RSDN
Автор: jazzer
Дата: 26.11.09

You will always get what you always got
  If you always do  what you always did
Re[3]: default constructor
От: Кодт Россия  
Дата: 20.05.04 11:40
Оценка:
Здравствуйте, UGN, Вы писали:

К>>Вообще же, если класс CopyConstructible и Assignable, то побочные эффекты (здесь — вывод в консоль) в конструкторах, деструкторе и присваивании лучше не делать. Потому что иначе получается unspecified / implementation-defined behaviour, то есть — как повезёт.


UGN>Это вывод из отдельных положений стандарта или там есть отдельный пункт с таким утверждением?


Отдельного пункта нет. Однако же, если ты не можешь, исходя из синтаксиса, утверждать — сколько раз и в каком порядке будет выполнена некая функция (здесь: тело деструктора) — то это и есть unspecified behaviour.

UGN>И что еще считать побочным эффектом?


Например, вывод в консоль.

Ничего локально-катастрофичного в таких побочных эффектах нет, но если от них зависит логика программы, то она может здорово пострадать.
Перекуём баги на фичи!
Re[4]: default constructor
От: Mr. None Россия http://mrnone.blogspot.com
Дата: 20.05.04 11:49
Оценка:
Здравствуйте, Кодт, Вы писали:

К>Отдельного пункта нет. Однако же, если ты не можешь, исходя из синтаксиса, утверждать — сколько раз и в каком порядке будет выполнена некая функция (здесь: тело деструктора) — то это и есть unspecified behaviour.


UGN>>И что еще считать побочным эффектом?


К>Например, вывод в консоль.


К>Ничего локально-катастрофичного в таких побочных эффектах нет, но если от них зависит логика программы, то она может здорово пострадать.


Не согласен... Сколько раз будет вызван тот или иной конструктор — это действительно предугадать сложно. Но сколько раз будет вызван деструктор можно сказать точно — столько же, сколько и все конструкторы данного класса. По-моему этого вполне достаточно. Я не представляю как в данном случае побочное поведение, например, вывод в консоль, может разрушить логику программы?
Компьютер сделает всё, что вы ему скажете, но это может сильно отличаться от того, что вы имели в виду.
Re[4]: default constructor
От: UGN  
Дата: 20.05.04 11:55
Оценка:
Здравствуйте, Кодт, Вы писали:

UGN>>И что еще считать побочным эффектом?


К>Например, вывод в консоль.


Ну, про консоль ты уже упоминал.

Вопрос в другом.

Каково определение побочных эффектов в С++?

К>Ничего локально-катастрофичного в таких побочных эффектах нет, но если от них зависит логика программы, то она может здорово пострадать.


А вот о чем 1.9/1 с примечанием 5 говорит?
Re[4]: default constructor
От: WolfHound  
Дата: 20.05.04 12:07
Оценка:
Здравствуйте, Кодт, Вы писали:

UGN>>Это вывод из отдельных положений стандарта или там есть отдельный пункт с таким утверждением?


К>Отдельного пункта нет. Однако же, если ты не можешь, исходя из синтаксиса, утверждать — сколько раз и в каком порядке будет выполнена некая функция (здесь: тело деструктора) — то это и есть unspecified behaviour.

RVO/NRVO
... << RSDN@Home 1.1.3 beta 1 >>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[5]: default constructor
От: folk Россия  
Дата: 20.05.04 12:36
Оценка:
Здравствуйте, UGN, Вы писали:

UGN>Каково определение побочных эффектов в С++?


Вроде это: 1.9/7

Accessing an object designated by a volatile lvalue (basic.lval), modifying an object, calling a library I/O function, or calling a function that does any of those operations are all side effects, which are changes in the state of the execution environment. ...

На самом деле, люди не читают газеты, они принимают их каждое утро, так же как ванну. ©Маршалл Мак-Льюэн
Re[7]: default constructor
От: Павел Кузнецов  
Дата: 20.05.04 20:48
Оценка: 17 (1)
> L_L>Так плевать на интел. У VC то как? Смотри, кстати, 8.5.3 / 5 , стр. 148, то место, где 93)
>
> Я собственно не веню компилятор в том что он вызывает 2 раза деструктор, а не один, проблема то в другом. Почему от того, есть ли конструктор или нет, зависит его поведение, и потом так сильно. Малоли что я могу делать в своей программе в этом деструкторе, а потом добавлю конструктор и ее поведение поменяется коренным образом. Как то это не правельно.

Естественно, неправильно. Т.е. неправильно, то что поведение твоей программы так радикально меняется от лишнего копирования. Стандарт явно разрешает компилятору как вводить неявные копии объектов (см. ссылки выше), так и оптимизировать "лишние" вызовы конструкторов копирования вне зависимости от наличия побочных эффектов в конструкторе копирования и деструкторе:

12.8/15 When certain criteria are met, an implementation is allowed to omit the copy construction of a class object, even if the copy constructor and/or destructor for the object have side effects.

Posted via RSDN NNTP Server 1.9 alpha
Легче одурачить людей, чем убедить их в том, что они одурачены. — Марк Твен
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.