Слабые справочные преимущества

Может кто-нибудь объяснить основные преимущества различных типов ссылок в С#?

  • Слабые ссылки
  • Мягкие ссылки
  • Phantom ссылки
  • Сильные ссылки.

У нас есть приложение, которое потребляет много памяти, и мы пытаемся определить, является ли это областью для фокусировки.

Ответ 1

Софт и phantom ссылаются на Java, я полагаю. Длинная слабая ссылка (переходите к конструктору С# WeakReference) можно считать аналогичной Java PhantomReference. Если в С# есть аналог SoftReference, я не знаю, что это такое.

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

Будет ли это полезно для снижения потребления памяти вашим приложением, будет полностью зависеть от специфики приложения. Например, если у вас умеренное количество кэшированных объектов, которые могут или не могут быть повторно использованы в будущем, слабые ссылки могут помочь улучшить потребление памяти в кэшах. Однако, если приложение работает с очень большим количеством мелких объектов, слабые ссылки затруднят работу, поскольку ссылочные объекты будут занимать столько же или больше памяти.

Ответ 2

MSDN имеет хорошее объяснение слабых ссылок. Ключевая цитата внизу, где говорится:

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

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

Ответ 3

Блестящий реальный пример с WeakReference объясняется в учебнике по разработке Android.

В представлении (ImageView) есть изображение (битмап) и контейнер изображений. Если изображение будет загружено не из памяти (но, например, с диска, сети), тогда оно может заблокировать поток пользовательского интерфейса и экран. Чтобы избежать этого, можно использовать асинхронную задачу.

Проблема возникает при завершении задачи async. Контейнер с изображениями может быть непригодным вообще в это время (экран изменен или Android выгружает невидимую часть просмотра после прокрутки). WeakReference может помочь здесь, и ImageView будет собирать мусор.

class BitmapWorkerTask extends AsyncTask<Integer, Void, Bitmap> {
    private final WeakReference<ImageView> imageViewReference;

    public BitmapWorkerTask(ImageView imageView) {
        imageViewReference = new WeakReference<ImageView>(imageView);
    }
    // Method for getting bitmap is removed for code clearness

    // Once complete, see if ImageView is still around and set bitmap.
    @Override
    protected void onPostExecute(Bitmap bitmap) {
        if (imageViewReference != null && bitmap != null) {
            final ImageView imageView = imageViewReference.get();
            if (imageView != null) {
                imageView.setImageBitmap(bitmap);
            }
        }
    }
}

P.S. пример находится в Java, но может быть понят разработчиками С#.
Источник: http://developersdev.blogspot.ru/2014/01/weakreference-example.html