1 2
Временный объект - auto_ptr в избранное  новое горячее всё    подписка   модер. 
От: TailWind 
Дата: 24.05.08 20:17
Нет ли здесь ошибки:

int Work( int *i) { return (*i) * 2; }

auto_ptr<int> Get() { auto_ptr<int> I( new int );  *I = 2;  return I; }

main()
{
  int a = Work( &*Get() );  // Нет ли здесь ошибки?
}
Re: Временный объект - auto_ptr в избранное  новое    модер. 
От: Erop 
Дата: 24.05.08 20:31
Здравствуйте, TailWind, Вы писали:

TW>Нет ли здесь ошибки:


В целом код корректный, конечно, но зачем так прогать?
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[2]: Временный объект - auto_ptr в избранное  новое    модер. 
От: TailWind 
Дата: 24.05.08 20:55
TW>>Нет ли здесь ошибки:
E>В целом код корректный, конечно, но зачем так прогать? :shuffle:

У меня там не int.
А базовый класс.

Функция Get не знает заранее какой наследник вернёт.
Поэтому по значению вернуть не получается.
Приходится возвращать auto_ptr.

Функция Work работает с указателем на базовый класс.
Вот и приходится огород городить...
Похоже по другому никак...

Вот ищу компактные формы ;)
Re[3]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Erop 
Дата: 24.05.08 21:30
Здравствуйте, TailWind, Вы писали:

TW>Вот ищу компактные формы

Лучше ищи явные и читабельные формы . IMHO это перспективнее.
Ещё Work можешь с const auto_ptr<xxx>& перегрузить попробовать
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[4]: Временный объект - auto_ptr в избранное  новое    модер. 
От: TailWind 
Дата: 24.05.08 21:37
E>Лучше ищи явные и читабельные формы :). IMHO это перспективнее.
Например?
В какой стороне искать?

E>Ещё Work можешь с const auto_ptr<xxx>& перегрузить попробовать :shuffle:

Да, это будет удобней ;)
Re[5]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Erop 
Дата: 24.05.08 22:03
Здравствуйте, TailWind, Вы писали:

E>>Лучше ищи явные и читабельные формы . IMHO это перспективнее.

TW>Например?
TW>В какой стороне искать?

Ну лично мне код вроде
auto_ptr<XXX> x = Get();
Work( &*x );
x = 0;

Оно поустойчивее к правкам прототипов всех этих функций будет. Либо будет работать, либо не скомпилируется, типа...

E>>Ещё Work можешь с const auto_ptr<xxx>& перегрузить попробовать

TW>Да, это будет удобней

Ну наслаждайся. Дарю. Можешь сказать "спасибо"
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[6]: Временный объект - auto_ptr в избранное  новое    модер. 
От: TailWind 
Дата: 24.05.08 23:08
Оценка:32 (3) :))) :)
E>Ну наслаждайся. Дарю. Можешь сказать "спасибо" :)
Конечно, спасибо ;)
Re[6]: Временный объект - auto_ptr в избранное  новое    модер. 
От: uzhas 
Дата: 25.05.08 12:35
Оценка: +1
E>Ну лично мне код вроде
auto_ptr<XXX> x = Get();
E>Work( &*x );
E>x = 0;

А по мне другой вариант приятнее
 std::auto_ptr<XXX> x = Get();
 Work(x.get());
 x.reset();

Здесь видно, что сигнатура функции Work() неудачна. Хорошо бы ее переделать на const XXX& или auto_ptr<XXX>&, тогда код превратился бы в

 std::auto_ptr<XXX> x = Get();
 assert(x.get() && "Empty pointer deref.");
 Work(*x);
 x.reset();
Re: Временный объект - auto_ptr в избранное  новое    модер. 
От: Zigmar 
Дата: 25.05.08 13:36
Здравствуйте, TailWind, Вы писали:

TW>Нет ли здесь ошибки:


TW>
TW>int Work( int *i) { return (*i) * 2; }

TW>auto_ptr<int> Get() { auto_ptr<int> I( new int );  *I = 2;  return I; }

TW>main()
TW>{
TW>  int a = Work( &*Get() );  // Нет ли здесь ошибки?
TW>}
TW>

Ошибки нет, но я бы вообще не рекомендовал бы пользоваться auto_ptr — уж очень опасная вешь. Копирование, при котором изменяется значение копируемого элемента — вещь не интуитивная, и потенциальный источник ошибок и недопониманий. ИМХО, если значение передавать не надо, то лучше использовать scoped_ptr, как,кстати, и выглядел auto_ptr в ранних версиях стандарта, пока к нему не прикрутили странную семантику передачи значения, сделав из него недо-смарт-поинтер. А если владение нужно передавать, то логично взять полноценный shared_ptr, linked_ptr или кого-нибудь из этой компании.
"To protect people you must slay people. To let people live you must let people die. This is the true teaching of the sword."
-Seijuro Hiko, "Rurouni Kensin"
Re[2]: Временный объект - auto_ptr в избранное  новое    модер. 
От: TailWind 
Дата: 25.05.08 14:56
Да меня эти auto_ptr<xxxx> по всему коду уже совсем достали.
Места много на эране занимают.
Не полиморфные, в отличии от указателей...
Но как без них непонятно.

А вопрос был вот в чём:
Функция Get() возвращает временный объект.
Потом я из него беру адресс внутренней переменной.
И передаю его в функцию Work.

Вопрос: Не удалится ли временный объект до выполнения функции Work
Re[3]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Erop 
Дата: 25.05.08 15:04
Здравствуйте, TailWind, Вы писали:

TW>Вопрос: Не удалится ли временный объект до выполнения функции Work

В том коде, который ты написал не удалится. Но может случиться и такой код, что удалится...
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re: Поискал в книжках в избранное  новое    модер. 
От: TailWind 
Дата: 25.05.08 20:23
Поискал в книжках.
Точно моего случая не нашёл.

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

То есть в моём варианте лучше сделать:
int Work(int &i) {..}


Верно?
Re[2]: Поискал в книжках в избранное  новое    модер. 
От: Roman Odaisky 
Дата: 25.05.08 20:33
Здравствуйте, TailWind, Вы писали:

TW>Но понял вот что:

TW>— временный объект держится если передавать ссылку
Только если ссылка константная, иначе ни о каком временном объекте не может идти речи.

TW>— удаляется, если передавать указатель

delete простому указателю никто не сделает. Удалится, если передавать «умный» указатель.
status=sent (delivered to file: /dev/null)
Re[3]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Maxim S. Shatskih mvp 
Дата: 26.05.08 00:10
TW>Функция Get не знает заранее какой наследник вернёт.
TW>Поэтому по значению вернуть не получается.
TW>Приходится возвращать auto_ptr.

TW>Функция Work работает с указателем на базовый класс.

TW>Вот и приходится огород городить...
TW>Похоже по другому никак...

Это что — полиморфные объекты по значению куда-то передаем, что ли?
Занимайтесь LoveCraftом, а не WarCraftом!
Re[7]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Maxim S. Shatskih mvp 
Дата: 26.05.08 00:11
U>Здесь видно, что сигнатура функции Work() неудачна. Хорошо бы ее переделать на const XXX& или auto_ptr<XXX>&

А еще лучше переделать на XXX* или const XXX*
Занимайтесь LoveCraftом, а не WarCraftом!
Re[3]: Временный объект - auto_ptr в избранное  новое    модер. 
От: Maxim S. Shatskih mvp 
Дата: 26.05.08 00:12
TW>Да меня эти auto_ptr<xxxx> по всему коду уже совсем достали.
TW>Места много на эране занимают.
TW>Не полиморфные, в отличии от указателей...

Почему? в auto_ptr<Base> можно засунуть Derived*
Занимайтесь LoveCraftом, а не WarCraftом!
Re[2]: Поискал в книжках в избранное  новое    модер. 
От: Maxim S. Shatskih mvp 
Дата: 26.05.08 00:13
TW>int Work(int &i) {..}

Ссылки и полиморфизм противоречат друг другу, я не прав?

(до каких только извращений люди не дойдут, только чтоб Base* не передавать).
Занимайтесь LoveCraftом, а не WarCraftом!
Re[3]: Поискал в книжках в избранное  новое    модер. 
От: Erop 
Дата: 26.05.08 04:02
Здравствуйте, Maxim S. Shatskih, Вы писали:

TW>>int Work(int &i) {..}


MSS>Ссылки и полиморфизм противоречат друг другу, я не прав?


почему?
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re: Временный объект - auto_ptr в избранное  новое    модер. 
От: Erop 
Дата: 26.05.08 04:33
Здравствуйте, TailWind, Вы писали:

TW>Нет ли здесь ошибки:


Было бы классно разобраться что где зачем и почему делается. Потом понять кто кем когда и сколько влдаеет, и только потом писать код, в котором эти вопросы решаются очевидно. Лично мне кажется, что обычно std::auto_ptr не совсем хорошо выражает семантику владения.

Когда-то, давно, он обозначал следующую парадигму программирования:
1) Хочешь передать невладеющий указатель -- передавай T*
2) Хочешь передать владение -- передавай std::auto_ptr...
Если уж хочется пользоваться std::auto_ptr, то изволь разобраться в своих функциях и следовать везде эттм правилам. Я не совсем понимаю, что и как в твоих функциях, но могу предположить. Вот смотри:
std::auto_ptr<X> Get(); // Возвращает владеющий указатель, поэтому auto_ptr
void Work( X* ); // Принимает невладеющий указатель, поэтому auto_ptr
Теперь мы имеем такой код:
std::auto_ptr<X> scope_owner = Get(); // Передали влдадение автоматическому объекту scope_owner
Work( scope_owner.get() ); // Передали невладеющий указатель
scope_owner = 0; // как вариант scope_owner.release() -- явно разрушили объект


При этом читателю такого кода не надо напрягаться и думать/понимать что там да как получится в случае чего. Всё управление владением в этом коде прописанно явно

Какие тут могут быть ещё варианты?
1) Передавать в Work не указатель, а ссылку.
Основная идея такая, что многие предполагают, что внутри Work ссылку на передаваемый объект запоминать нельзя, а указатель можно (такие правила кодирования используют). Соответсвенно таким требуется передавать в Work ссылку. При явном управлении владением ничего особо не меняется. Просто вместо scope_owner.get() пишешь *scope_owner и всё. Но от парадигмы использования std::auto_ptr шаг в стороны таки сделан...

2) Можно передавать в Work const std::auto_ptr<X>&
Основная идея такая, что при таком раскладе аргумент Work точно переживёт вызов, и очевидно, что запоминать аргумент нельзя. Основной недостаток такой, что если твоя версия STL допускает неявное конструирование std::auto_ptr, можно нарваться так
X x; 
Work( &x ); // Ups
Ну и вообще ограничивается то, где может располагаться объект X. Типа только в куче. Хотя, может быть, это и требуется.

3) Управлять владением неявно
Скажем так
Work( Get().get() );
Это ещё куда ни шло, хотя код стал зело непрозрачным, IMHO. Надо таки понимать что ту делается и кто чем владеет, так как явно это в коде нигде не выражено...

Лично я предпочёл бы либо писать управление владением явно, либо передавать по значению объекты имеющие семантику значения. Чтобы вообще о владении этими объектами не парится. Типа все автоматические и всё. В твойм случае это обозначало бы, например использование shared_ptr<X> той или иной версии. Конечно это слегка менее эффективно, зато код писать проще...
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Теги: 
Re[4]: Временный объект - auto_ptr в избранное  новое    модер. 
От: TailWind 
Дата: 26.05.08 07:16
Здравствуйте, Maxim S. Shatskih, Вы писали:

TW>>Функция Get не знает заранее какой наследник вернёт.

TW>>Поэтому по значению вернуть не получается.
TW>>Приходится возвращать auto_ptr.

TW>>Функция Work работает с указателем на базовый класс.

TW>>Вот и приходится огород городить...
TW>>Похоже по другому никак...

MSS>Это что — полиморфные объекты по значению куда-то передаем, что ли?


Почему?
В auto_ptr
Как ссылку
Как указатель
1 2