Очистка структур данных .NET для GC - PullRequest
2 голосов
/ 20 июня 2011

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

Помогает ли GC быстрее освободить памятькогда меньше ссылок (более простой график ГХ)?

Ответы [ 3 ]

4 голосов
/ 20 июня 2011

Нет, это не так.Если «родительский» объект недоступен, то его «дочерние» ссылки в любом случае не будут проходить, поэтому они не имеют значения.

Что более важно, код очистки обычно действует как отвлечение от реальный код. очень редко стоит явно установить переменные в null и т. Д., Чтобы помочь сборщику мусора.* бывают случаев, когда это стоит делать, но обычно они предлагают, что, возможно, вам следует все равно реорганизовать свой код (например, использовать меньшие методы, если вы устанавливали локальные переменные в null, или создавать меньшие объекты, если вы устанавливали экземплярпеременные к нулю).

0 голосов
/ 21 июня 2011

Существуют две примечательные ситуации, в которых установка нуля ускоряет сборку мусора:

  1. Переменная содержит ссылку, которая фактически никогда больше не будет использоваться, но код таков, что компиляторне могу этого сказать.Обратите внимание, что при отладке переменные хранятся до тех пор, пока они находятся в области видимости, независимо от того, будут ли они использоваться снова (среди прочего, поскольку оператор может принудительно использовать их снова, устанавливая точку выполнения в более раннее положениев текущей области), но в сборках релиза компилятор может отказаться от переменных, которые больше не будут использоваться (обратите внимание, что это может, если не соблюдать осторожность, вызвать ошибки, связанные с Finalize!)
  2. Если поколение-2объект содержит ссылку на объект поколения 0, объект поколения 0 не будет иметь права на коллекцию, пока не будет создана полная коллекция поколения 2.Этого может не случиться довольно долго.Очистка ссылки позволит собрать объект поколения 0 намного раньше.
  3. Если объект, который необходимо сохранить живым, имеет одно или несколько полей, содержащих ссылки, которые больше не будут использоваться, очистка этих ссылок поможет сборщику мусора.

Если у вас нет оснований полагать, что одна из этих ситуаций может существовать, удаление ссылок вряд ли будет полезным.Может показаться, что первая ситуация часто возникает при отладке, но если нет причин полагать, что компилятор не распознает переменную как устаревшую, не стоит беспокоиться об этом.Второй может произойти во время отладки или производства, но конкретные обстоятельства, необходимые для его возникновения, не очень распространены.Третий - тот, о котором стоит больше всего беспокоиться.Распространенная вариация возникает, когда класс содержит массив ссылок на объекты вместе с полем «size», которое указывает, сколько элементов массива являются «значимыми».Существует четыре способа «очистить» такую ​​структуру:

  1. Просто установите поле размера на ноль
  2. Установите поле размера на ноль и перераспределите новый (возможно, меньший) массив,отказаться от старого.
  3. Установите поле размера в ноль и очистите все элементы массива.
  4. Установите поле размера на ноль, очистите все элементы массива, а затем оставьте массив и выделите новый

Установка поля размера на ноль - самый быстрый способ «логически» очиститьвне структуры данных.Однако, если он не будет заполнен таким количеством предметов, сколько у него было, он сохранит ссылки на оставленные элементы.Выделение нового массива и отказ от старого позволят избежать этой проблемы, но если этот массив существовал некоторое время, это может привести к ситуации № 2, упомянутой выше.Очистка всех элементов массива, но сохранение самого массива может быть лучшим подходом, если массив не особенно велик.Очистка всех элементов и отказ от массива может быть лучшим подходом, если массив большой, и структура данных вряд ли будет немедленно перезаписана чем-то близким к числу элементов, которые у него были.

0 голосов
/ 20 июня 2011

Редактировать: Вместо того, чтобы удалить сообщение, как и было обещано, я проверил текст и, как я подозревал, еще до ухода с работы, что я был неправ. Я ценю, что мистер Скит прямо не назвал меня кровавым идиотом на форуме, хотя он, вероятно, хотел. Я не уверен, откуда у меня эта идея застряла в моей голове даже после прочтения текста, на который я ссылаюсь, в котором есть фантастическое описание того, как работает схема сбора мусора. В любом случае, я прошу прощения и признаю свою ошибку. Ворона имеет плохой вкус, но я учился на своих странных путях:)

CLR сохраняет индексатор для каждого созданного объекта и увеличивается / уменьшается по мере продвижения выполнения. Когда счетчик ссылок на объект достигает нуля, это выделение памяти планируется для сборки мусора. Ссылки могут быть уменьшены с помощью объекта, выходящего из области видимости, объекта, имеющего значение NULL, или вызываемых членов интерфейса IDisposable. Целью реализации IDisposable для ваших классов будет очистка ресурсов, не являющихся POCO, или использование системных ресурсов, которые не очищаются автоматически, таких как дескрипторы файлов, соединения с базой данных, сетевые потоки и т. Д. В противном случае, когда объект выходит из Объем памяти будет очищен во время следующего цикла ГХ.

...