Как я знаю, кто держит shared_ptr <>?

alloca () хороша и эффективна ... но она также глубоко сломана.

  • нарушено поведение области (область действия функции вместо области видимости блока)
  • использование несовместимо с malloc (указатель с [alloca alloca () не должен быть освобожден, отныне вы должны отслеживать, откуда приходят ваши указатели на free () только те, которые вы получили с malloc () )
  • плохим поведением, когда вы также используете встраивание (область действия иногда переходит к функция вызывающего абонента в зависимости от того, включен ли вызываемый абонент или нет).
  • нет проверки границы стека
  • неопределенное поведение в случае сбоя (не возвращает NULL, как malloc ... и что означает сбой, так как в любом случае он не проверяет границы стека ...)
  • не соответствует стандарту

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

Если вам действительно нужно это C, вы можете использовать VLA (нет vla в C ++, тоже неплохо). Они намного лучше, чем alloca () в отношении поведения и согласованности области видимости. Как я вижу, VLA являются своего рода alloca () , сделанными правильно.

Конечно, локальная структура или массив, использующий мажоранту необходимого пространства, все еще лучше, и если у вас нет такого мажорантного выделения кучи с использованием обычного malloc (), вероятно, это нормально. Я не вижу ни одного нормального варианта использования, где вам действительно нужно alloca () или VLA.

11
задан GManNickG 30 June 2009 в 03:59
поделиться

7 ответов

Вы не можете узнать, просто посмотрев на shared_ptr , где находятся "указатели на родственные связи". Вы можете проверить, является ли один из unique () , или получить use_count () среди других методов .

21
ответ дан 3 December 2019 в 01:04
поделиться

You may be experiencing a shared pointer memory leak via cycles. What happens is your shared objects may hold references to other shared objects which eventually lead back to the original. When this happens the cycle keeps all reference counts at 1 even though no one else can access the objects. The solution is weak pointers.

3
ответ дан 3 December 2019 в 01:04
поделиться

Вы, очевидно, держитесь за ссылки на свои объекты внутри вашего применение. Это означает, что вы намеренно храните вещи в памяти. Это означает, что у вас нет утечки памяти. Утечка памяти - это когда память выделяется, а затем вы не сохраняете ссылку на ее адрес.

По сути, вам нужно посмотреть на свой дизайн и выяснить, почему вы храните так много объектов и данных в памяти и как вы можете минимизировать это.

Одна из возможных причин утечки псевдопамяти заключается в том, что вы создаете больше объектов, чем думаете. Попробуйте поставить точки останова на все операторы, содержащие «новый». Посмотрите, создает ли ваше приложение больше объектов, чем вы думали, и затем прочтите этот код.

Проблема на самом деле не столько в утечке памяти, сколько в дизайне вашего приложения.

1
ответ дан 3 December 2019 в 01:04
поделиться

Попробуйте провести рефакторинг некоторого кода, чтобы право владения выражалось более явно с помощью слабых указателей вместо общие указатели в некоторых местах.

Если посмотреть на иерархию классов, это ' s можно определить, какой класс действительно должен содержать общий указатель, а какой нужен только слабый, так что вы можете избежать циклов, если они есть, и если "реальный" объект-владелец разрушен, объекты "не-владельцы" уже должны иметь отсутствовал. Если выясняется, что некоторые объекты теряют указатели слишком рано, вам необходимо изучить последовательность уничтожения объектов в своем приложении и исправить ее.

3
ответ дан 3 December 2019 в 01:04
поделиться

Невозможно определить, какие объекты владеют shared_ptr из программы. Если вы работаете в Linux, надежным способом отладки утечек памяти является инструмент Valgrind . Хотя он не отвечает напрямую на ваш вопрос, он сообщит, где была выделена память, что обычно достаточно для устранение проблемы. Я полагаю, что в Windows есть аналогичные инструменты, но я не знаю, какой из них лучше.

-1
ответ дан 3 December 2019 в 01:04
поделиться

Широко распространенное использование shared_ptr почти неизбежно приведет к нежелательному и невидимому использованию памяти.

Циклические ссылки - хорошо известная причина, и некоторые из них могут быть косвенными, и их трудно обнаружить, особенно в сложных код, над которым работают более чем один программист; программист может решить, что одному объекту нужна ссылка на другой в качестве быстрого исправления, и у него нет времени исследовать весь код, чтобы увидеть, закрывает ли он цикл. Эта опасность сильно недооценивается.

Менее понятна проблема невыпущенных ссылок. Если объект совместно используется многими shared_ptr, он не будет уничтожен, пока каждый из них не будет обнулен или не выйдет за пределы области видимости. Очень легко упустить одну из этих ссылок и в конечном итоге получить невидимые в памяти объекты, которые, как вы думали, вы закончили. 1. Заявление о том, что вы действительно хотите стать единоличным владельцем, как shared_ptr. scoped_ptr будет правильным, но тогда любая другая ссылка на этот объект должна быть необработанным указателем, который можно оставить висящим. 2. Объявление того, что вы действительно хотите, чтобы пассивная ссылка наблюдения, как shared_ptr. weak_ptr будет правильным, но тогда у вас возникнут проблемы с преобразованием его в share_ptr каждый раз, когда вы захотите его использовать.

Я подозреваю, что ваш проект является прекрасным примером проблем, в которые эта практика может вас втянуть.

Если у вас есть приложение, интенсивно использующее память, вам действительно нужно единоличное владение, чтобы ваш проект мог явно контролировать время жизни объекта.

При единственном владении opObject = NULL; обязательно удалит объект, и он сделает это сейчас.

При совместном владении spObject = NULL; ........ кто знает? ......

12
ответ дан 3 December 2019 в 01:04
поделиться

Я собирался предложить использовать UMDH, если вы работаете в Windows. Это очень мощный инструмент. Используйте его, чтобы найти распределения на транзакцию / период времени, которые вы ожидаете освободить, а затем найдите, кто их держит.

Подробнее об этом ответе SO Найдите утечки памяти, вызванные интеллектуальными указателями

1
ответ дан 3 December 2019 в 01:04
поделиться
Другие вопросы по тегам:

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