Android Bitmap loading multiple images cache processing (Essence II)

Source: Internet
Author: User

Generally a few pictures are rarely oom abnormal, unless the single picture too ~ Big ~ then you can use the method inside the tutorial
Usually the application scenario is that the ListView list loads multiple pictures, in order to improve the efficiency of the general to cache a portion of the picture, so easy to see again when you can quickly display ~ do not re-download pictures
But the phone memory is very limited ~ when the cached picture is more and more, even if the single picture is not very large, but the number of too many will still appear in the situation of Oom ~
This article is to discuss the processing of multiple images

-----------------------------------------------------------------------

The general processing of the picture cache is
1. Create a picture buffer pool for storing the bitmap object of the image
2. In the display, such as the ListView to the Ching adapter GetView method to load the image of the work, first from the buffer pool through the URL of the key value, if the image is taken directly display,
If you do not get the async thread again to download the picture (download it and save it to the image cache pool and display it)

But the cache pool can not be infinitely large AH ~ Otherwise it will be abnormal, so usually we have to control the cache pool
There are two features required:
There is a limit to the total size, otherwise there will be an infinite number of images stored in the memory overflow Oom exception
When the size reaches the upper limit, and then add the picture, it is necessary for the thread pool to intelligently reclaim a portion of the image in the pool, so that the display of the new picture can be saved


Asynchronous thread download Picture God horse simple, online asynchronous download task code a lot, download after stream data directly decode into bitmap picture can
The difficulty in the design with this image cache pool, now the implementation of the network mainly have two
1. Soft reference/Weak reference
2.LruCache

-----------------------------------------------------------------------

Extension: 4 Types of reference categories in Java
Official Information Link: http://developer.android.com/reference/java/lang/ref/Reference.html
Strong references
Normal use of the basic is a strong reference, unless the active release (image collection, or ==null assignment is empty, etc.), or will persist the object until memory overflow ~
Soft reference SoftReference
When the system is low on memory, it automatically releases the objects that are referred to as soft references ~
Weak reference WeakReference
The system occasionally recycles the scan to find the weak reference to release the object, that is, not enough memory to be independent of the situation, completely look at the mood ~
Virtual reference
I don't know, but I'm not familiar with it.

The framework is basically more like using this soft app to save the image as a cache pool, so that when the picture is too low, it will automatically reclaim some pictures, prevent oom
But there are shortcomings, can not control the memory is not enough to recycle which pictures, if I just want to recycle some of the infrequently used, do not recycle commonly used pictures?


So we introduced the logic of level two cache.
That is, set two cache pools, a strong reference, a soft reference, strong references to save common images, soft apps to save other pictures ~
Strong references because the object is not automatically released, so the size must be limited, or too many pictures will be abnormal, such as the control of only 10 pictures stored inside,
And then every time you add a picture to it, check if the number exceeds 10 of this threshold, the threshold value,
Remove the most infrequently used image from the strong reference and save it to the soft app cache pool ~


The entire cache is both as a whole (a level two cache is a memory cache ~ Check the entire cache pool for pictures before each picture is displayed)
There is a certain distinction (only two cache soft references in the image, do not reclaim the first-level cache strongly referenced pictures ~)




Code implementation
Soft application cache pool type as level two cache:
hashmap<string, softreference<bitmap>> msecondlevelcache = new hashmap<string, SoftReference< Bitmap>> ();
Strong references are used as first-level caches, in order to implement the deletion of the least commonly used objects, you can use the Linkedhashmap<string,bitmap> class

The Linkedhashmap object can replicate a removeeldestentry, which is used to handle the deletion of the least common object logic.
This can be written according to the previous design:

Final int max_capacity = 10; First level cache threshold value

The first parameter is the size of the initialization
The second parameter, 0.75, is the load factor as an empirical value
The third parameter, True, indicates the order of the most recent visits, and False indicates that they are sorted according to the insertion sequence
hashmap<string, bitmap> mfirstlevelcache = new linkedhashmap<string, bitmap> (
MAX_CAPACITY/2, 0.75f, True) {
Eldest oldest object, which is the most infrequently used picture object to remove
A return value of True removes the object, false does not remove
Protected Boolean removeeldestentry (Entry<string, bitmap> eldest) {
if (size () > Max_capacity) {//When the total size of the cache pool exceeds the threshold, move the old value from the first level cache to level two cache
Msecondlevelcache.put (Eldest.getkey (),
New Softreference<bitmap> (Eldest.getvalue ()));
return true;
}
return false;
}
};


Each time the picture is displayed, if it exists with the cache, the object is removed from the cache and then added back to the front end of the first-level cache
There's going to be three different things.
1. If the picture is taken from a primary cache, it is equivalent to moving the object to the front of the first-level cache pool (equivalent to a recently used picture) ~
2. If the picture is taken from the level two cache, it will be saved to the front of the first level cache pool and detected, and if the threshold is exceeded, move the least common object to the level two cache
3. If not in the cache, then download the image on the Internet, download it and save it to the first level cache, again to detect whether to remove an object to the level two cache

-----------------------------------------------------------------------

In conjunction with real-world examples (if the above logic is understood to be skipped):
American basketball, for example, has a top-level league NBA and a sub-level league nbdl~
The first-League NBA rankings are ranked according to the last time the championship was taken from near to far,
We stipulate that every quarter of the game to produce a champion, the championship may be any of the existing team may also be a new team to the private ~
And when a team to win the championship, he added to a team in the NBA ~ because it is the last time to win the championship, so add in the time is also ranked first

NBA as the highest level, we have a limit on the number, so every time there is a new champion when we have to do a test,
If the total number of teams is more than 20, remove the worst team that has been the longest since the last time it was won.


If the championship is the equivalent of a picture using a quarterly match, the above three cases correspond to our example:
1.NBA team to win the championship, the equivalent of the ranks of the team to become the first ~ but the total number of NBA team, there is no new to join
2.NBDL two league won the championship, then added to the NBA, and became the first ~ because the NBA team equivalent to the increase of one, it is necessary to test whether more than 20 and the worst results of the squeeze into the NBDL
3. The people come to the great God abuse all the team took the championship, that directly into the NBA and then become the first, the same, testing the number of NBA teams to determine whether to squeeze out a team

The NBDL team is equivalent to the soft application of the level two cache pool, no Limit quantity ~ How much can be, until the United States basket maintenance all NBA NBDL team funds is not enough (the image is too much to apply memory)
will automatically dissolve a portion of the team, fall into the civil, until the next time to win the championship and then join (the equivalent of the image removed from the cache, the next use to re-download) ~
The NBA is the equivalent of a first-class cache, often win (equivalent to high-frequency use of images), then we do not want to be due to the lack of funds randomly disbanded several teams just to dissolve the NBA team,
If the funds are not enough, only to dissolve the two-level league NBDL Team ~ because they get a lower chance of competition ~

The civil team exists outside the league system (the equivalent of no images in the cache), and any NBA NBDL League team we can understand as a folk promotion to come over ~
Only from the folk to win the championship and join the league need a name AH registration AH and so on procedures (download pictures), more trouble, so we have to do as little as possible procedures ~
The league team (including NBA NBDL) won the championship without the hassle of formalities, can directly participate in the competition to win the Championship (direct access to the display)


Two leagues, a commonly used limited number, an uncommon number of unqualified, but not sufficient funds to automatically reclaim some of the two-level team ~
A level two cache equivalent to a picture

-----------------------------------------------------------------------

Disk Cache
It can be easily understood to cache the image in the SD card ~

Because the memory cache is emptied when the program is closed for the second time, for a very common image such as avatar type ~
We do not want to go to the application every time the download again, it will use disk cache, the direct image is stored locally, open the app directly to get the display ~

The most logical order to get pictures online is
Get display in memory cache (strong reference cache pool, weak reference cache pool)--not found in memory when get display----in cache from SD card cache no more asynchronous threads downloaded picture, saved to cache after download is complete

According to the speed of obtaining the image efficiency, from fast to slow to try several methods

Cached in the form of files to the SD card, the advantage is that the SD card capacity is large, so you can cache a lot of pictures, and multiple open apps can use the cache,
The disadvantage is that file read and write operations take a little time,
Although speed does not get faster from the memory cache, it is certainly faster than downloading one image at a time-and you don't have to download the picture everytime to waste traffic ~
So using the priority is between the memory cache and the downloaded picture.

Attention:
SD card cache is generally to be carried out in advance whether or not to load the SD card detection, but also to detect the availability of the SD card remaining capacity is sufficient
The program should also add the appropriate permissions

-----------------------------------------------------------------------

Using LRUCache to process picture caches

The above basic completely mastered, each picture best again to carry on the tutorial (a) inside the single-sheet scaling processing, that basic entire picture cache technology is almost
But with the Android SDK update, the new version actually provides a better solution, the following introduction

See the old version of the soft reference official document
Http://developer.android.com/reference/java/lang/ref/SoftReference.html
Introduction to soft references in extract segments
Avoid Soft References for Caching

In practice, soft references is inefficient for caching. The runtime doesn ' t has enough information on which references to clear and which to keep. Most fatally, it doesn ' t know-what does when given the choice between clearing a soft reference and growing the heap.
The lack of information on the value to your application of each reference limits the usefulness of soft references. References that is cleared too early cause unnecessary work; Those that is cleared too late waste memory.

Most applications should use an android.util.LruCache instead of soft references. LruCache has a effective eviction policy and lets the user tune how much memory is allotted.

A simple translation

We want to avoid using soft references to handle caching

In practice, soft references are inefficient in the processing of caches. The runtime does not have enough information to determine which references to clean up and what to save.
The most deadly, when faced with both cleaning soft references and adding heap memory to both options, it does not know what to do.
There is a lack of valuable information for every reference you apply, which limits the availability of soft references to limited use.
Premature cleanup of recycled references leads to unnecessary work; And those late-cleanup references wasted memory.

Most applications should use a android.util. LRUCache instead of soft references. The LRUCache has an effective recycling mechanism that allows users to adjust how much memory is allocated.



In short, using the soft reference cache directly is not a good effect ~ Recommended use of LRUCache
Level12 introduced later, in order to be compatible with earlier versions, the ANDROID-SUPPORT-V4 package also added a LRUCache class,
So in the 12 version above with the words found that there are two of the package has this class, in fact, are the same ~

So what does this class do? This is the official document.
Http://developer.android.com/reference/android/util/LruCache.html

LRU means that least recently used is the least recently used algorithm ~
Familiar, in fact, the previous two-level cache of the strong reference linkedhashmap processing logic is actually an LRU algorithm
And we look at the source code of this class LRUCache found in fact there is also a linkedhashmap, probably swept the eye, the logic and we wrote the same as before
The core functions are basically: when new data is added and thresholds are reached, a minimum of data is removed


According to this new class to do the picture loading, most of the online practice is still two-level cache processing
Just a soft reference to the linkedhashmap+
Replaced with lrucache+ soft reference
are level two cache, strong reference + Soft reference structure ~ because LRUCache and Linkedhashmap are all about the same processing logic
Does not remove the use of soft references, but combines the two together

According to the introduction of the official website, in fact, soft reference effect is not small, two-level cache processing, although can improve a little effect, but will waste memory consumption ~
So do not add a soft reference to the level two cache, the specific choice to see their own understanding and practical application of the scene

LRUCache I understand is sacrificing a small fraction of efficiency, in exchange for some memory ~ I personally also tend to use only the LRUCache implementation without soft references, but also relatively simple ~


Combined with the previous example can be understood as, directly cancel the NBDL two league (soft reference) ~ This can save a great amount of money (memory) and then invest in other aspects of the league (processing other logic)
and expand the size of the next NBA Premier League (LruCache)-to ensure reuse efficiency

-----------------------------------------------------------------------

Specific usage of LRUCache

Before the linkedhashmap have a certain understanding, in fact, LRUCache is similar
The recycling logic, similar to the Removeeldestentry method, has been processed in this class.
Normally we just have to deal with the control of the threshold.

The core method of threshold control is the sizeof () method, which means that the size of each value object is returned size~
The default is to return 1~ that is, when MaxSize (passed by constructor) is set to 10, it is equivalent to limiting the cache pool to 10 objects only ~
And the example above Linkedhashmap a meaning


But because of the size of the picture, generally limit the total size of all the pictures more appropriate, then we can make the sizeof method of replication
@Override
protected int sizeOf (String key, Bitmap value) {
return Value.getrowbytes () * Value.getheight ();
}
In this case, the equivalent of the size of each object in the cache pool is the number of bytes that are computed, then a total size value is passed when the new LRUCache is created.
1/8 size of available memory for general incoming apps

-----------------------------------------------------------------------

This article is a discussion of the number of pictures of the control problem, and then combined with the tutorial (a) in the method of each picture to the corresponding processing ~oom the situation basically can be avoided ~

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.