Растровые изображения в Android

У меня есть несколько вопросов относительно объектов и памяти Bitmap и их общей таксономии.

  1. Что такое встроенное bitmap в памяти?
  2. Чем отличается память битмапа от памяти кучи?

Память, которая поддерживает объект Bitmap, выделяется с использованием собственного кода ( malloc() ), а не ключевого слова Java new . Это означает, что память управляется непосредственно ОС, а не Dalvik.

Единственное реальное различие между нативной кучей и кучей Dalvik заключается в том, что куча Dalvik – это garbage collection, а родной – нет.

Однако для этих целей здесь нет большой разницы. Когда ваш объект Bitmap получает garbage collection, он деструктор будет перерабатывать связанную память в нативной куче.

Источник:

Здесь есть важная тонкость: хотя пиксели Bitmap выделяются в нативной куче, некоторые специальные трюки в Dalvik заставляют ее учитывать Java кучу. Это делается по двум причинам:

(1) Для управления объемом памяти приложение распределяет это. Без учета приложение может выделять огромное количество памяти (так как сам объект Bitmap очень мал, но может удержаться на произвольно большой объем встроенной памяти), выходящий за пределы 16-мегабайтного или 24-мегабайтного кучи.

(2) Чтобы определить, когда GC. Без учета вы могли бы выделять и выпускать ссылки на 100 объектов Bitmap; GC не будет работать, потому что эти объекты являются крошечными, но на самом деле они могут представлять собой большое количество мегабайт фактических распределений, которые теперь не GCed своевременно. Учет этих распределений против кучи Java, сборщик мусора будет работать, поскольку он считает, что память используется.

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

Из развертываний в дикой природе я нашел следующие устройства:

  • Устройства, которые ограничивают 16 мегабайт кучи java (растровые изображения почти неограничены).
  • Устройства, которые ограничены 16 мегабайтами (java heap + native bitmap storage)
  • Устройства, которые ограничивают 24 мегабайта кучи java (растровые изображения почти неограничены).
  • Устройства, которые ограничены 24 мегабайтами (java heap + native bitmap storage)

24 MiB имеет тенденцию быть устройствами с высоким разрешением и может быть обнаружен с помощью Runtime.getRuntime (). MaxMemory (). Также есть 32-мегабайтные устройства, а некоторые из корневых телефонов по умолчанию имеют 64MiB. Раньше я несколько раз путал себя, пытаясь понять, что происходит. Я думаю, что все устройства подсчитывают растровые изображения в пределе кучи. Но очень сложно сделать какие-либо широкие обобщения об андроидном флоте.

Это ОЧЕНЬ неприятная проблема на Android и очень запутанная. Этот предел и его поведение плохо документированы, сложны и крайне неинтуитивны. Они также различаются в разных устройствах и версиях ОС и имеют несколько известных ошибок. Частью проблемы является то, что пределы не точны – из-за fragmentации кучи, вы попадете в OOM задолго до фактического предела и должны консервативно оставить мега или два буфера. Хуже того, у меня есть несколько устройств, где есть собственный segfault (100% ошибка в самом Android), которая возникает до того, как вы получите исключение Java OOM, что делает его вдвойне важным никогда не достигать предела, поскольку вы даже не можете поймать родной аварии. Для получения дополнительной информации о моих расследованиях, ознакомьтесь с этим сообщением . В том же сообщении я объясняю, как измерить использование против лимита и избежать сбоев.

Размер кучи java – это Runtime.getRuntime (). TotalMemory ().

Нет простого способа измерения размера собственного растрового хранилища. Общая нативная куча может быть измерена с помощью Debug.getNativeHeapAllocatedSize (), но только растровые изображения подсчитываются до предела (я думаю).

Мы можем увеличить размер кучи, используя android:largeheap="true" в вашем файле манифеста. Это решит вашу проблему.

  • Android: Как работает Bitmap recycle ()?
  • Определите, работает ли на корневом устройстве
  • Исправлено столбец IOException, записывающий сериализуемый объект getactivity ()
  • Изменить текст и действие кнопки - разработка Android-приложений
  • Получить текущее время и дату на Android
  • Android: Как растянуть изображение до ширины экрана при сохранении пропорций?
  • Поворот растрового изображения с использованием JNI & NDK
  • Рисование зеркальных растровых изображений в android
  • Запись / чтение файлов в / из внутренней памяти телефона Android
  • При выходе из системы очистите стек истории событий, не позволяя кнопке «Назад» открывать только зарегистрированные.
  • ANDROID: Как получить root-доступ в приложении для Android?
  • Interesting Posts
    Давайте будем гением компьютера.