Почему это неправильно для использования станд.:: auto_ptr <> со стандартными контейнерами?

Другое событие NullPointerException возникает, когда объявляется массив объектов, а затем сразу же пытается разыменовать его внутри.

String[] phrases = new String[10];
String keyPhrase = "Bird";
for(String phrase : phrases) {
    System.out.println(phrase.equals(keyPhrase));
}

Этот конкретный NPE можно избежать, если порядок сравнения отменяется ; а именно, использовать .equals для гарантированного непустого объекта.

Все элементы внутри массива инициализируются их общим начальным значением ; для любого типа массива объектов, это означает, что все элементы null.

Вы должны инициализировать элементы в массиве перед доступом или разыменованием их.

String[] phrases = new String[] {"The bird", "A bird", "My bird", "Bird"};
String keyPhrase = "Bird";
for(String phrase : phrases) {
    System.out.println(phrase.equals(keyPhrase));
}

208
задан Lightness Races with Monica 14 December 2011 в 01:06
поделиться

5 ответов

В Стандарте C++ говорится, что элемент STL должен быть "конструируемым копией" и "присваиваемым". Другими словами, элемент должен быть в состоянии быть присвоенным или скопированным, и эти два элемента логически независимы. std::auto_ptr не выполняет это требование.

Берут, например, этот код:

class X
{
};

std::vector<std::auto_ptr<X> > vecX;
vecX.push_back(new X);

std::auto_ptr<X> pX = vecX[0];  // vecX[0] is assigned NULL.

Для преодоления этого ограничения необходимо использовать std::unique_ptr , std::shared_ptr или std::weak_ptr интеллектуальные указатели или эквиваленты повышения, если у Вас нет C++ 11. Вот документация библиотеки повышения для этих интеллектуальных указателей.

123
ответ дан 6 revs, 5 users 80% 23 November 2019 в 04:41
поделиться

семантика копии из auto_ptr не совместимы с контейнерами.

А именно, копируя один auto_ptr другому не создает два равных объекта, так как каждый потерял его владение указателя.

А именно, копируя auto_ptr причины одна из копий для отпущения указателя. То, которое из них остается в контейнере, не определяется. Поэтому можно случайным образом потерять доступ к указателям, если Вы храните auto_ptrs в контейнерах.

65
ответ дан Frank Krueger 23 November 2019 в 04:41
поделиться

Контейнеры STL должны быть в состоянии скопировать объекты, которые Вы храните в них и разработаны, чтобы ожидать, что оригинал и копия будут эквивалентны. автоматические объекты указателя имеют совершенно другой контракт, посредством чего копирование создает передачу права собственности. Это означает, что контейнеры auto_ptr покажут странное поведение, в зависимости от использования.

существует подробное описание того, что может пойти не так, как надо в Эффективном STL (Scott Meyers) объект 8 и также not-so-detailed описание в Эффективном C++ (Scott Meyers) объект 13.

17
ответ дан Lazer 23 November 2019 в 04:41
поделиться

Контейнеры STL хранят копии содержавших объектов. Когда auto_ptr копируется, он устанавливает старый ptr в NULL. Много методов контейнера повреждаются этим поведением.

12
ответ дан Dustin Getz 23 November 2019 в 04:41
поделиться

Две превосходные статьи на эту тему:

38
ответ дан 23 November 2019 в 04:41
поделиться
Другие вопросы по тегам:

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