SharedPreference 你的使用姿势对吗?
发布日期:2021-05-08 00:09:53 浏览次数:20 分类:精选文章

本文共 4482 字,大约阅读时间需要 14 分钟。

1. commit 和 apply 的区别

commit 返回一个 boolean 来表明修改是否提交成功, apply 没有返回值;commit 是将数据写入内存后同步提交到磁盘(不要在主线程中 commit ),而 apply 将数据写入内存后会在一个新线程中异步提交到磁盘,在不要求提交结果的情况下应使用 apply。

2. 批量操作

当我们一次有多个修改写操作时,不要多次 edit 和 apply,尽量批量修改一次提交

3. 第一次加载 & 存储大的 key value

sp 底层是以xml方式进行数据存储的,在第一次使用的时候会加载整个文件加载进入内存,接下来的读操作都是内存缓存操作而不是文件操作。sp 在加载的时候确实是异步加载,但是在 sp 文件加载未完成时 getString() setString() 等方法是阻塞等待的。所以不要在 sp 存放大的 key 和 value ,会拖慢第一次加载时的速度,引起界面卡顿;同时解析 sp(xml的解析) 还会产生很多临时对象导致频繁GC;并且这些 key 和 value 将永远存在于内存之中,占用大量内存。

4. 存储 json or html ?

这么做不是不可以,但是,如果这个 json 相对较大,那么也会引起 sp 读取速度的急剧下降。json 或者 html 格式存放在sp里面的时候,需要转义,这样会带来很多 & 这种特殊符号, sp 在解析碰到这个特殊符号的时候会进行特殊的处理,引发额外的字符串拼接以及函数调用开销。

5. sSharedPrefsCache

ContextImpl 有一个 static 的 ArrayMap 变量 sSharedPrefsCache,它保存了你应用中所有的 sp ,sSharedPrefsCache 在应用启动以后首次使用 SharePreference 时创建,系统结束时才可能会被垃圾回收器回收,在这个过程中你程序中使用到的那些个 sp 将永远呆在内存中,如果 App 中频繁的使用不同文件名的 SharedPreferences 这让这个 Map 变得很大,占用大量内存。

6. 一个应用只使用一个 sp ?

别闹了,要知道 sp 在第一次加载的时候会把整个文件加载进内存,文件越大读取速度越慢。

正确的做法:

  • 将 key 按照使用是否频繁分类,经常使用的放在一个 sp ,几乎不用的放在另一个 sp。
  • 将相关性高、经常一起使用的 key 放在一个 sp。
  • 其实就是一个内存与速度的平衡关系,建议偏重速度。

7. 多进程

sp 不支持多进程,即使你使用了 MODE_MULTI_PROCESS 也是不行的。

8. registerOnSharedPreferenceChangeListener

这个方法可以监听 sp 的数据变化,非常方便

SPUtil

Skip to contentPersonal Open source Business ExploreSign upSign inPricingBlogSupportThis repositorySearch Watch 0  Star 1  Fork 2 ssyijiu/android-helper Code  Issues 1  Pull requests 0  Projects 0  Pulse  GraphsBranch: master Find file Copy pathandroid-helper/utils/SPUtil.java412bcb1  on 25 Oct@ssyijiu ssyijiu update SPUtil1 contributorRawBlameHistory     110 lines (83 sloc)  3.06 KBpackage com.ssyijiu.ahelper;import android.content.Context;import android.content.SharedPreferences;import com.ssyijiu.library.MLog;/** * * 批量提交数据请使用: * SPUtil.getEditor(context).putString(key,value).putInt(key,value).apply(); * * 单次提交数据直接使用:SPUtil.putString(); * */public class SPUtil {    private static SharedPreferences sSP;    private static SharedPreferences.Editor sEditor;    private SPUtil() {        /* cannot be instantiated */        throw new UnsupportedOperationException("SPUtil cannot be instantiated !");    }    private static SharedPreferences getInstance(Context context) {        if (sSP == null) {            sSP = context.getSharedPreferences("config", Context.MODE_PRIVATE);        }        return sSP;    }    public static SharedPreferences.Editor getEditor(Context context) {        if(sEditor == null) {            sEditor = getInstance(context).edit();        }        return sEditor;    }    public static void putBoolean(Context context, String key, boolean value) {        sSP = getInstance(context);        sSP.edit().putBoolean(key, value).apply();    }    public static void putString(Context context, String key, String value) {        sSP = getInstance(context);        sSP.edit().putString(key, value).apply();    }    public static void putInt(Context context, String key, int value) {        sSP = getInstance(context);        sSP.edit().putInt(key, value).apply();    }    public static boolean getBoolean(Context context, String key, boolean defValue) {        sSP = getInstance(context);        return sSP.getBoolean(key, defValue);    }    public static String getString(Context context, String key, String defValue) {        sSP = getInstance(context);        return sSP.getString(key, defValue);    }    public static int getInt(Context context, String key, int defValue) {        sSP = getInstance(context);        return sSP.getInt(key, defValue);    }    public static void remove(Context context, String key) {        sSP = getInstance(context);        sSP.edit().remove(key).apply();    }    public static void clear(Context context, String key) {        sSP = getInstance(context);        sSP.edit().clear().apply();    }    public static boolean contains(Context context, String key) {        sSP = getInstance(context);        return sSP.contains(key);    }    public static void registerOnSharedPreferenceChangeListener(Context context, SharedPreferences.OnSharedPreferenceChangeListener listener) {        if(listener != null) {            sSP = getInstance(context);            sSP.registerOnSharedPreferenceChangeListener(listener);        }    }    public static void unregisterOnSharedPreferenceChangeListener(Context context, SharedPreferences.OnSharedPreferenceChangeListener listener) {        if(listener != null) {            sSP = getInstance(context);            sSP.unregisterOnSharedPreferenceChangeListener(listener);        }    }}

上一篇:我的2016
下一篇:android app中的权限及自定义权限

发表评论

最新留言

路过按个爪印,很不错,赞一个!
[***.219.124.196]2025年04月01日 12时31分15秒