Onsharedpreferencechangelistener details and the emergence of no triggering solution _android

Source: Internet
Author: User
Tags garbage collection modifier

Before using Onsharedpreferencechangelistener, there is a small problem, that is, sometimes onsharedpreferencechangelistener is not triggered. Recently spent a little time studying, small do tidy up. This article will explain why the listener is not triggered, how to fix it, and some of the technical details implied therein.

Problem reappearance

Onsharedpreferencechangelistener is a listener for changes in sharedpreference files in Android. Usually we want to listen, and we will implement the following code.

protected void OnCreate (Bundle savedinstancestate) {
 preferencemanager.getdefaultsharedpreferences ( Getapplicationcontext ())
  . Registeronsharedpreferencechangelistener (New Onsharedpreferencechangelistener () {
  @Override public
  void onsharedpreferencechanged (
   sharedpreferences sharedpreferences, String key) {
   log.i (LogTag, "testonsharedpreferencechangedwrong key =" + key);
  }
 );
}

This style of writing does not seem to be a problem, and many times the Onsharedpreferencechanged method can be invoked. But over time (simple demo is not easy to come by, but using GC in DDMS will immediately cause the next problem), you will find that the previous method is suddenly no longer invoked, which in turn affects the processing of the program.

Cause analysis

In short, your registered listener has been removed.
First, let's take a look at the implementation of Registeronsharedpreferencechangelistener registration.

Private final Weakhashmap<onsharedpreferencechangelistener, object> mlisteners =
   new weakhashmap< Onsharedpreferencechangelistener, object> ();
Some code goes here is public void more ...
registeronsharedpreferencechangelistener ( Onsharedpreferencechangelistener listener) {
 synchronized (this) {
  mlisteners.put (Listener, mcontent);
 }
}

As you can see from the code above, a Onsharedpreferencechangelistener object is actually placed in a Weakhashmap container, and after the OnCreate method in the example, the Listener object will soon be the target of garbage collection. , because a key in Weakhashmap does not prevent garbage collection, the listener is removed from the mlisteners after the listener object is reclaimed. So it caused the onsharedpreferencechanged not to be invoked.

For weakhashmap related, read: Understand weak references in Java and learn more about them.

How to Solve

Change to object member variable (recommended)

The listener is used as a member variable of the activity, registered at the onresume of the activity, and logged out at OnPause. This is recommended for processing in these two activity lifecycles, especially when the sharedpreference values are changed to handle the UI being displayed by the event. This approach is the most recommended solution.

Private Onsharedpreferencechangelistener Mlistener = new Onsharedpreferencechangelistener () {

 @Override
 public void onsharedpreferencechanged (
  sharedpreferences sharedpreferences, String key) {
  log.i (LogTag, " Instance variable key= "+ key";
 }
};

@Override
protected void Onresume () {
 preferencemanager.getdefaultsharedpreferences (getapplicationcontext ()). Registeronsharedpreferencechangelistener (Mlistener);
 Super.onresume ();
}

@Override
protected void OnPause () {
 preferencemanager.getdefaultsharedpreferences ( Getapplicationcontext ()). Unregisteronsharedpreferencechangelistener (Mlistener);
 Super.onpause ();
}

Change to static variable (not recommended)

as follows, a variable slistener that points to an anonymous internal class object is used with the static modifier, which does not hold a reference to the external class.
This practice is not recommended, however, because a static variable is not relevant to an external instance, and it is difficult to do something with an external instance.

private static Onsharedpreferencechangelistener Slistener = new Onsharedpreferencechangelistener () {
 @Override Public
 void onsharedpreferencechanged (
  sharedpreferences sharedpreferences, String key) {
  log.i (LogTag, "Static variable key=" + key);
 }
;

Why do you design this way

Some might think that this is a trick or a bug in the system design, which is the genius of Android designers.

As our example code, adding an (implicit) local variable to the listener container, if the container is just a normal hashmap, can cause a memory leak because the container also has an object that the local variable points to, and that object implicitly holds the object of the external activity. Causes the activity to not be destroyed. For a non-static inner class holding an implicit hold of an external class reference, refer to the private modifier of the Java: invalid

In addition, because local variables cannot be accessed outside of the method in which they are located, we can only use local variables in the method to register the row, but we cannot use local variables to log off at the right time.

The above is the introduction of the Android Onsharedpreferencechangelistener, as well as the problem solution, thank you for your support to this site!

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.