The context is the object that we often use to write Android programs, meaning contextual objects. The context in which activity is commonly used is still application. Activity is used to show the active interface, contains a lot of views, and the view contains pictures, text and other resources. Memory leaks are easy to come up on Android, and the activity that holds many objects in memory is more prone to memory leaks, and developers need to pay special attention to this problem.
This article describes the Android context, more specifically, the activity memory leaks, and how to avoid activity memory leaks and accelerate application performance.
Memory leaks caused by drawable
The problem of drawable causing memory leaks is more obscure and imperceptible. Read the Romain Guy's avoiding memory leaks, combined with grepcode to see the source code just understand.
In the Android system, when we do a screen rotation, by default, the current activity is destroyed and a new activity is created and the previous state is maintained. In this process, the Android system reloads the program's UI views and resources. Suppose we have a program that uses a large bitmap image, and we don't want to reload the bitmap object each time the screen rotates, the easiest way is to use the static modifier for the bitmap object.
private static drawable Sbackground;
@Override
protected void onCreate (Bundle state) {
super.oncreate (state);
TextView label = new TextView (this);
Label.settext ("Leaks are bad");
if (Sbackground = = null) {
Sbackground = getdrawable (R.drawable.large_bitmap);
}
Label.setbackgrounddrawable (sbackground);
Setcontentview (label);
However, the above method may cause memory leaks when the screen is rotated, and it is difficult to find out where the memory leaks are caused by looking at the code or looking at it carefully.
When a drawable is bound to the view, the View object actually becomes a callback member variable of this drawable, in the example above the static sbackground holds the reference TextView object lable, Lable only refers to the activity, and the activity holds references to other objects. Sbackground life cycle is longer than activity. When the screen rotates, the activity cannot be destroyed, which creates a memory leak problem.
Implementation of the Setcallback method of 2.3.7 and the following version drawable
Public final void Setcallback (Callback cb) {
mcallback = cb;
}
Fortunately, starting with 4.0.1, weak references are introduced to handle this problem, and weak references are not prevented from retrieving the objects they point to when GC is reclaimed, so that the problem of memory leaks is avoided.
Public final void Setcallback (Callback cb) {
mcallback = new weakreference<callback> (CB);
Single-Case memory leaks
A single example is one of the more common design patterns we use, but it can also lead to memory leaks if a single example is used incorrectly. For example, we use a hungry man to initialize a single example, appsettings we need to hold a context as a member variable, if we follow the following implementation is actually a problem.
public class AppSettings {
private context mappcontext;
private static AppSettings sinstance = new AppSettings ();
Some other codes public
static AppSettings getinstance () {return
sinstance;
}
Public final void Setup (context context) {
Mappcontext = context;
}
}
Sinstance as a static object with a life cycle longer than a normal object, which also contains activity, when we rotate the screen, the system destroys the current activity by default, and the current activity is held by a single instance, causing the garbage collector to not recycle , resulting in a memory leak.
The solution is not to hold the reference to the activity, but to hold the application context reference. The code is modified as follows
Public final void Setup (context context) {
mappcontext = Context.getapplicationcontext ();
}
Visit here to learn more about the single case mode problem
All methods return to context
Usually we want to get the context object, there are mainly four ways
- View.getcontext, returns the context object for the current view object, usually the activity object that is currently being displayed.
- Activity.getapplicationcontext, gets the context object for the current activity's (application) process, which is usually given priority when we use it.
- Contextwrapper.getbasecontext (): Used to get a contextwrapper to decorate the context before, you can use this method, this method in the actual development of the use of not much, also do not recommend use.
- Activity.this returns the current activity instance, if the UI control needs to use an activity as the context object, but the default toast actually uses ApplicationContext.
Other memory leak issues
The bad Asynctask in Android
Memory leaks caused by handler in Android
Onsharedpreferencechangelistener and the emergence of no triggering solution
Avoid memory leaks keep in mind
- Do not allow a life cycle longer than an activity object to hold a reference to an activity
- Try to use the context of application rather than the context of activity
- Try not to use non-static inner classes in the activity, because non-static inner classes implicitly hold references to external class instances (specifically, you can see the private modifiers of the Java: "Invalid"). If you use a static inner class, hold the external instance reference as a weak reference.
- Garbage collection does not solve memory leaks, understand the garbage collection mechanism in Android
Reference articles
Avoiding memory leaks
difference between GetContext (), Getapplicationcontext (), Getbasecontext () and "This"
Android–what ' s The difference between the various methods to get a context?
The above is the Android context memory leak data collation, follow-up continue to add relevant information, thank you for your support!