Analyze several possible _android of the Android memory leak

Source: Internet
Author: User
Tags garbage collection message queue

Objective

Memory leak simply means that you have applied for a piece of memory space and have not been released after use. Its general performance is the longer the program runs, the more memory consumed, the end of the total memory, the entire system crashes. A piece of memory that is requested by the program, and none of the pointers point to it, the memory is compromised.

From the user's point of view of the program, the memory leak itself will not produce any harm, as a general user, do not feel the existence of memory leaks. What really harms is the accumulation of memory leaks, which ultimately consumes all the memory of the system. In this sense, a one-time memory leak is harmless because it does not accumulate, and the implicit memory leak is very harmful because it is more difficult to detect than frequent and accidental memory leaks.

Java is a garbage collection language, the advantage is that developers do not have to deliberately manage memory allocation, reduce the application due to local failure (segmentation fault) caused by the crash, while preventing the release of memory to the stack (heap), so the written code is more secure.

Unfortunately, there are still a lot of logic in Java that can easily lead to memory leaks (logical leak). If you're not careful, your Android app can easily waste memory that's not released, and it could end up with bugs that run out of memory.(out-of-memory,OOM)

the reason for the general memory leak (traditional memory leak) is that when all references to the object have been freed, the object has not been released. (Translator Note: Cursor forget to close etc.)

the reason for the logical memory leak (logical memory leak) is that when this object is no longer needed by the application, all references to that object are still not released.

If you hold a strong reference to an object, the garbage collector cannot reclaim the object in memory.

In Android development, the most easily raised memory leaks are the context. The context of an activity, for example, contains a large number of memory references, such as view hierarchies and other resources. Once the context is leaked, it also means leaking all the objects it points to. The Android machine has limited memory, and too much memory leaks can easily lead to oom.

Detecting logical memory leaks requires subjective judgment, especially when the life cycle of objects is not clear. Fortunately, the activity has a clear lifecycle and it is easy to spot the cause of the leak. Activity.onDestroy()is seen as the end of an activity's life, it should be destroyed in the program, or the Android system needs to recycle the memory (Android will recycle unseen activity when there is not enough memory).

If this method is done, there is still a strong reference on the stack that holds the activity, and the garbage collector cannot mark it as reclaimed memory, and our intention is to reclaim it!

The result is that the activity survives its life cycle.

Activity is a heavyweight object that should be handled by the Android system. However, logical memory leaks are always inadvertently occurring. (Translator Note: One activity has been tried to cause a 20M memory leak). In Android, the pitfalls that lead to potential memory leaks are of two kinds:

The static variable for the global Process (Process-global) . This ignores the application of the state, holding the strong reference to the activity of the monster.

A thread that lives outside the activity lifecycle. A strong reference to the activity was not emptied.

Check to see if you have encountered the following situation.

Static Activities

A static activity variable is defined in the class, and the currently running activity instance is assigned to this static variable.

If this static variable is not emptied at the end of the activity lifecycle, it causes a memory leak. Because the static variable runs through the lifecycle of the application, the exposed activity will always exist in the application process and will not be reclaimed by the garbage collector.

static activity activity;
 
void Setstaticactivity () {Activity
   = this;
}
 
View Sabutton = Findviewbyid (R.id.sa_button);
Sabutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Setstaticactivity ();
     Nextactivity ();
   }
);

Memory Leak 1–static Activity

Static views

Similar situations can occur in singleton mode, and it is useful to save an instance in memory if the activity is often used. As mentioned earlier, it is quite dangerous and unnecessary to force the life cycle of an activity to be prolonged, and it cannot be done in any way.

Special case: If a view initialization consumes a lot of resources and remains unchanged during an activity lifecycle, it can be static and loaded into the view hierachy, like this, when the activity is destroyed , resources should be released. (Translator Note: the example code does not release memory, this static view is null can be, but still do not recommend this static view method)

static view;
 
void Setstaticview () {
  view = Findviewbyid (R.id.sv_button);
}
 
View Svbutton = Findviewbyid (R.id.sv_button);
Svbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Setstaticview ();
     Nextactivity ();
   }
);

Memory Leak 2–static View

Inner Classes

Continue, assuming that there is an internal class in the activity, which can improve readability and encapsulation. Will be like we create an inner class, and hold a reference to a static variable, congratulations, the memory leak is not far away from you (translator Note: Empty when destroying, um).

private static Object inner;
 
void Createinnerclass () {
   class Innerclass {
   }
   inner = new Innerclass ();
}
 
View Icbutton = Findviewbyid (R.id.ic_button);
Icbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Createinnerclass ();
     Nextactivity ();
   }
);

Memory Leak 3–inner Class

One of the advantages of an inner class is that it can access the external class, which, unfortunately, causes the memory leak because the inner class holds a strong reference to the external class instance.

Anonymous Classes

Similarly, anonymous classes maintain references to external classes. So memory leaks are easy to happen when you define anonymous Asynctsk in activity

。 When an asynchronous task performs a time-consuming task in the background, the activity is unfortunately destroyed (the translator notes: The user exits, the system recycles), and the activity instance that is held by the asynctask is not reclaimed by the garbage collector until the asynchronous task ends.

void StartAsyncTask () {
   new asynctask<void, Void, void> () {
     @Override protected void doinbackground (void ... params) {while
        (true);
     }
   . Execute ();
}
 
Super.oncreate (savedinstancestate);
Setcontentview (r.layout.activity_main);
View Aicbutton = Findviewbyid (R.id.at_button);
Aicbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     StartAsyncTask ();
     Nextactivity ();
   }
);


Memory Leak 4–asynctask

Handler

In the same way, define anonymous runnable, handler execution with anonymous classes. The runnable inner class holds an implicit reference to the external class, is passed to the handler message Queue MessageQueue, and the activity instance is not destroyed until the message messages are processed, resulting in a memory leak.

void Createhandler () {
new Handler () {
   @Override public void handlemessage (Message message) {
     Super.handlemessage (message);
   }
. Postdelayed (New Runnable () {
   @Override public void Run () {
   while (true);
}
}, Long.max_value >> 1) ;
}
 
View Hbutton = Findviewbyid (R.id.h_button);
Hbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
      Createhandler ();
      Nextactivity ();
   }
);

Memory Leak 5–handler

Threads

We again show memory leaks through thread and timertask.

void Spawnthread () {
new Thread () {
   @Override public void Run () {while
     (true);
   }
}. Start ();
}
 
View TButton = Findviewbyid (R.id.t_button);
Tbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Spawnthread ( );
     Nextactivity ();
   }
);


Memory Leak 6–thread

TimerTask

As long as an instance of an anonymous class, whether on a worker thread or not, holds a reference to the activity, causing a memory leak.

OID Scheduletimer () {
new Timer (). Schedule (new TimerTask () {
   @Override public
   Void Run ()
     ( true);
   }
, Long.max_value >> 1);
 
View Ttbutton = Findviewbyid (R.id.tt_button);
Ttbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Scheduletimer ();
     Nextactivity ();
   }
);


Memory Leak 7–timertask

Sensor Manager

Finally, a Context.getSystemService(int name) system service can be obtained. These services work in their respective processes, helping to apply background tasks and handle hardware interactions. If you need to use these services, you can register the listener, which causes the service to hold a reference to the context, which can cause a memory leak if you do not unregister these listeners when the activity is destroyed.

void Registerlistener () {
   Sensormanager Sensormanager = (sensormanager) getsystemservice (sensor_service);
   Sensor Sensor = Sensormanager.getdefaultsensor (sensor.type_all);
   Sensormanager.registerlistener (this, sensor, sensormanager.sensor_delay_fastest);
}
 
View Smbutton = Findviewbyid (R.id.sm_button);
Smbutton.setonclicklistener (New View.onclicklistener () {
   @Override public void OnClick (View v) {
     Registerlistener ();
     Nextactivity ();
   }
);


Memory Leak 8–sensor Manager

Summarize

The

has seen so many examples of memory leaks, that it is easy to eat up the memory of the phone to make garbage collection more frequent, or even the worst case can lead to oom. Garbage collection operations are expensive and can cause the naked eye to be visible to the cotton. So, when instantiated, pay attention to the chain of references held, and often carry out memory leak check. The purpose of this article is to let us in the development of how to effectively avoid the problem of memory leaks in our application. Hope to help you.

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.