Мы тестируем библиотеку под C ++ 11 (т.е. -std=c++11
). Библиотека использует auto_ptr
и этот шаблон:
Foo* GetFoo()
{
autoptr<Foo> ptr(new Foo);
// Initialize Foo
ptr->Initialize(...);
// Now configure remaining attributes
ptr->SomeSetting(...);
return ptr.release();
}
C ++ 11 устарел auto_ptr
, поэтому мы хотим от него отойти.
Тем не менее, код поддерживает как C ++ 03, так и C ++ 11, поэтому он не такой простой, как янки auto_ptr
. Стоит также упомянуть, что библиотека не имеет внешних зависимостей. Он использует C ++ 03; и не использует Autotools, Cmake, Boost, ...
Как мы должны обрабатывать изменения дизайна, чтобы отойти от auto_ptr
C ++ 11 при сохранении совместимости с C ++ 03?
auto_ptr
областей (то естьstd::auto_ptr
), они должны быть или умный указатель может быть получен из некоторого другого пространства имен?Foo::Initialize
вFoo::Foo
.Ответы:
В большинстве отношениях
std::unique_ptr
было сделано , чтобы быть падение (но безопаснее) замены дляstd::auto_ptr
, так что должно быть очень мало (если таковые имеются) изменения кода требуется , кроме (как вы спрашиваете) направлять код для использования либоunique_ptr
илиauto_ptr
.Есть несколько способов сделать это (и каждый из них имеет свой собственный компромисс со списком) ниже. Учитывая предоставленный пример кода, я бы предпочел любой из первых двух вариантов .
Опция 1
Компромисс;
auto_ptr
имя в глобальное пространство имен; Вы можете смягчить это, определив, что это ваше собственное "личное" пространство именauto_ptr
он будет полностью удален), вам будет проще искать и заменятьВариант 2
Компромисс;
auto_ptr
должны быть изменены в коде на что-то вродеmy_ptr<T>::ptr
Вариант 3
Несколько спорны, но если вы готовы мириться с предостережениями , имеющим
std
класс в качестве основыКомпромисс;
Вариант 4
Оберните указатели в новый класс и объедините необходимые функции для члена
Компромисс;
источник
tr1
пространства имен no там больше (я использую libc ++, а не libstdc ++). Я знаю, что tr1 был ненормативным, но я нигде не могу найти в черновике (здесь), что файлы должны быть<tr1/...>
вообще, в действительности он упоминает только о том, что находится в<memory>
файле заголовка и т. Д. Только вtr1
пространстве имен.CXX=...
).c++ -v -std=c++11 -x c++ - < /dev/null
. Яgrep'd
включил каталоги, которые были сброшены, и они не включаютunique_ptr
.Вариант 5: Прямой псевдоним.
Компромисс:
Для более новых языковых версий, AKA C ++ 11 и более поздних версий, ваш тип псевдонима соответствует правильному интеллектуальному указателю. Любой пользовательский код, который фактически зависит от API, специфичных для std :: auto_ptr, будет помечен компилятором, что является окончательной гарантией того, что он действительно будет исправлен.
В режиме Legacy c ++ 03 псевдоним типа является макросом. Это грубо, но результирующий синтаксис
MyPtr<T>
будет идентичен случаю C ++ 11 в остальной части кода.Вы должны найти и изменить все ваши переменные auto_ptr
MyPtr
, чтобы настроить это.источник