Activity之SharedPreferences探究(三)

2014-11-24 01:19:49 · 作者: · 浏览: 2
context.getPackageName() + "_preferences"; } 原来是传递了一个字符串,而且这个字符串是由当前APP的PackageName+_preferences组成。现在是否看出点什么呢? 我们知道一个APP可以有大量的activity和Service,他们的PackageName是一样的,难道一个APP所有的activity和Service都传递相同的一个字符串去获取一个SharedPreferences吗?

难道说一个一个APP所有的activity和Service都共享一个SharedPreferences? 是这样吗?我们继续往下看:


所以我们最终来关注context的getSharedPreferences函数的实现了。

我们知道Context.java里面只是Context定义了接口,真正实现这个接口的其实是在这里ContextImpl.java,所以我们很快找到了这个函数的定义:

    public SharedPreferences getSharedPreferences(String name, int mode) {
        SharedPreferencesImpl sp;
        synchronized (sSharedPrefs) {
            sp = sSharedPrefs.get(name);
            if (sp == null) {
                File prefsFile = getSharedPrefsFile(name);
                sp = new SharedPreferencesImpl(prefsFile, mode);
                sSharedPrefs.put(name, sp);
                return sp;
            }
        }
        if ((mode & Context.MODE_MULTI_PROCESS) != 0 ||
            getApplicationInfo().targetSdkVersion < android.os.Build.VERSION_CODES.HONEYCOMB) {
            // If somebody else (some other process) changed the prefs
            // file behind our back, we reload it.  This has been the
            // historical (if undocumented) behavior.
            sp.startReloadIfChangedUnexpectedly();
        }
        return sp;
    }
getSharedPreferences这个函数很简单:

(1)首先是通过传递进来的name来获取一个SharedPreferencesImpl实例,SharedPreferencesImpl已经在上面说过了,他其实就是一个SharedPreferences。这里是通过sSharedPrefs.get(name);这段代码来获取的,看一下sSharedPrefs这个量的定义你就会吓一跳:

    private static final HashMap
  
    sSharedPrefs =
            new HashMap
   
    ();
   
  
sSharedPrefs是一个私有的、最重要的是:还是一个静态的、并且还是一个final型的HashMap 的变量。这里最重要的要理解static:这表示sSharedPrefs是所有Context实例共享的,也就是说,原则上所有APP如此当前的存在可用的他们的SharedPreferences都是暂时存在这里的。

那么如果当前需要用的SharedPreferences在sSharedPrefs不存在,那怎么办? 当然是创建一个新的SharedPreferences,然后再加入到sSharedPrefs看看上面的这个函数: getSharedPreferences的实现就知道:

            if (sp == null) {
                File prefsFile = getSharedPrefsFile(name);
                sp = new SharedPreferencesImpl(prefsFile, mode);
                sSharedPrefs.put(name, sp);
                return sp;
            }
(1)上面我贴出来了创建一个新的SharedPreferences的代码。可以看出:先是通过name创建一个File 。我们来来看看到底是创建了什么文件:

    public File getSharedPrefsFile(String name) {
        return makeFilename(getPreferencesDir(), name + ".xml");
    }

看到了吧,这下就明白了,其实就是创建了一个.xml。而文件名其实就是这个name。回顾一下name其实就是这个APP的PackageName+_preferences组成。

(2)XML文件创建好了,接着sp = new SharedPreferencesImpl(prefsFile, mode);就创建了一个SharedPreferencesImpl实例。 我们回顾一下:在开始介绍SharedPreferencesImpl的实现的时候就说到了他的构造函数,这个构成函数的一个参数就是file,一个文件。 这下就知道了 ,这个文件其实就是一个XML文件。

所以:对于一个APP的SharedPreferences “all clients share”的意思就是:一个APP的所有clients share这个SharedPreferences 。而这里的 clients显然是指这个APP的所有activity和Service。