一、简介
SharePreference 是Android 系统中的持久化存储工具其基于XML文件(/data/data/<package name>/shared_prefs/目录下面),一次性将数据读取到内存中,适合单个进程、数据量较小的情况。
二、实践
使用SharedPreferences的正确姿势
1.1 创建SharedPreferences对象
SharedPreferences spf = context.getSharedPreferences("xx",Context.MODE_PRIVATE);
// MODE_PRIVATE,则该配置文件只能被自己的应用程序访问
// MODE_WORLD_READABLE,则该配置文件除了自己访问外还可以被其它应该程序读取
// MODE_WORLD_WRITEABLE,则该配置文件除了自己访问外还可以被其它应该程序读取和写入
// MODE_APPEND,检查文件是否存在,存在就往文件追加内容,否则就创建新文件
1.2 获得SharedPreferences.Editor对象。
SharedPreferences.Editor editor = spf.edit();
editor.putString(key, value);
1.3 插入、删除、查找key-value数据
editor.putString(key, value);
editor.remove(key);
editor.get(key,default-value);
Map<String,?> key_Value=(Map<String, ?>)spf.getAll();
// 获取所有保存在对应标识下的数据,并以Map形式返回
1.4 保存key-value数据
editor.apply(); // 异步
editor.commit(); // 同步
三、原理解析
/*
*xml对应的SharePreferences是否已经被创建加载,如果没有那么该创建就创建,
*该加载就加载,在加载之后,要将所有的key-value保存到内幕才能中去
*/
public SharedPreferences getSharedPreferences(String name, int mode) {
SharedPreferencesImpl sp;
synchronized (ContextImpl.class) {
if (sSharedPrefs == null) {
sSharedPrefs = new ArrayMap<String, ArrayMap<String, SharedPreferencesImpl>>();
}
final String packageName = getPackageName();
ArrayMap<String, SharedPreferencesImpl> packagePrefs = sSharedPrefs.get(packageName);
if (packagePrefs == null) {
packagePrefs = new ArrayMap<String, SharedPreferencesImpl>();
sSharedPrefs.put(packageName, packagePrefs);
}
sp = packagePrefs.get(name);
if (sp == null) {
// 读取XML文件
File prefsFile = getSharedPrefsFile(name);
sp = new SharedPreferencesImpl(prefsFile, mode);
// 缓存sp对象
packagePrefs.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;
}
SharedPreferencesImpl初始化
// 构造函数传入file 、mode
SharedPreferencesImpl(File file, int mode) {
mFile = file;
mBackupFile = makeBackupFile(file);
mMode = mode;
mLoaded = false;
mMap = null;
startLoadFromDisk();
}
// 加载XML文件到内存中
private void loadFromDiskLocked() {
...
Map map = null;
StructStat stat = null;
try {
stat = Os.stat(mFile.getPath());
if (mFile.canRead()) {
BufferedInputStream str = null;
try {
<!--读取xml中配置-->
str = new BufferedInputStream(
new FileInputStream(mFile), 16*1024);
map = XmlUtils.readMapXml(str);
}...
mLoaded = true;
...
<!--唤起其他等待线程-->
notifyAll();
}
四、总结
- SharePreferences是Android基于xml实现的一种数据持久化手段
- SharePreferences不支持多进程,不适合大数据量存储。
- SharePreferences的commit与apply前者同步方法、后者为异步
网友评论