Android - утечка памяти при динамическом построении пользовательского интерфейса с фоновыми изображениями - PullRequest
8 голосов
/ 10 января 2011

У меня есть активность, клянусь, утечка памяти.Приложение, над которым я работаю, много работает с изображениями, поэтому мне пришлось скупиться с памятью при работе непосредственно с растровыми изображениями.Я добавил Activity, и теперь, если вы используете эту новую Activity, она в основном ставит меня в тупик с использованием mem, и я в итоге выкидываю исключение «Bitmap превышает VM бюджет».Если вы никогда не запускаете это действие, все будет гладко, как было раньше.

Я начал читать об утечках памяти, и я думаю, что у меня ситуация, аналогичная описанной в статье в документации по Android.Я динамически создаю кучу видов изображений и добавляю BackgroundDrawable из ресурсов, а также добавляю OnClickListener.Я полагаю, что мне нужно провести некоторую очистку, когда Activity сталкивается с onPause в своем жизненном цикле, но я хотел бы знать, какой именно путь правильный.работа с ...

    LinearLayout templateContainer;
    .
    .
    .
    ImageView imgTemplatePreview = (ImageView) item.findViewById(R.id.imgTemplatePreview);
    .
    .
    .
    imgTemplatePreview.setBackgroundDrawable(getResources().getDrawable(previewId));
    imgTemplatePreview.setOnClickListener(imgClick);
    templateContainer.addView(item); 

Ответы [ 2 ]

2 голосов
/ 11 января 2011

Rich,

Если вы собираетесь иметь дело с таким количеством Bitmap s, вы должны агрессивно очистить их, когда они не нужны (onPause - хорошее начало).

Я помню дискуссию о ImageView s и их странном поведении с давними ссылками на их отображаемые растровые изображения.Из того, что я помню, вы должны удалить все ссылки на текущий контекст из ImageView, если вы собираетесь сохранить макет живым, но не хотите течь.Удалите прослушиватель onClick и растровое изображение.Позвоните .recycle() на Bitmap, если хотите активно освободить память.Убедитесь, что у вас нет статических полей с длительными ссылками на контекст или внутренними ссылками на него.

Код для программы запуска Android также упоминался в качестве хорошей ссылки, где они делают некоторые из этих вещей.,OpenSource - ваш друг.

РЕДАКТИРОВАТЬ

Найдена статья о Romain Guys.В основном он упоминает эту часть пути, хотя

Этот пример является одним из самых простых случаев утечки контекста, и вы можете увидеть, как мы работали с ним в исходном коде главного экрана (ищите unbindDrawables() метод, установив нулевые обратные вызовы хранимых элементов рисования при уничтожении действия.

Теперь мне никогда не приходилось управлять этим типом использования памяти (пока), поэтому здесь я предлагаю посмотретьна Источник исходного экрана для более подробной информации.Вы найдете их unbind() метод в строке 620

0 голосов
/ 11 января 2011

Это будет звучать немного странно, но у меня возникли проблемы с приложениями, которые выполняли какие-либо манипуляции с растровыми изображениями в потоке, отличном от того, который связан с обработчиком для вашей активности.В частности, у меня было приложение, которое утекло много памяти, выполняя манипуляции с изображениями в потоке java.util.Timer.Когда я перенес этот код на использование Handler.postDelayed, проблемы с памятью прояснились.

...