//获得SharedPreferences的实例 sp_name是文件名val sp: SharedPreferences = getSharedPreferences("sp_name", Context.MODE_PRIVATE)//获得Editor 实例val editor: SharedPreferences.Editor = sp.edit()//以key-value形式保存数据editor.putString("data_key", "data")//apply()是异步写入数据editor.apply()//commit()是同步写入数据 //editor.commit()
//获得SharedPreferences的实例val sp = getSharedPreferences("sp_name", MODE_PRIVATE)//通过key值获取到相应的data,如果没取到,则返回后面的默认值val data = sp.getString("data_key", "defaultValue")
通常项目中我们会封装成类似 SPUtil 的方式使用,但是 sp 使用起来还是稍显麻烦,下面就利用 by 委托机制对 sp 进行更优雅的封装。
/** * SharedPreferences委托代理 * @param context Context * @param spName SP存入的XML名字 * @param defaultValue 默认值 * @param key 存取数据时对应的key */class SharedPreferencesDelegate<T>( private val context: Context, private val spName: String, private val defaultValue: T, private val key: String? = null,) : ReadWriteProperty<Any?, T> { private val sp: SharedPreferences by lazy(LazyThreadSafetyMode.NONE) { context.getSharedPreferences(spName, Context.MODE_PRIVATE) } override fun getValue(thisRef: Any?, property: KProperty<*>): T { val finalKey = key ?: property.name return when (defaultValue) { is Int -> sp.getInt(finalKey, defaultValue) is Long -> sp.getLong(finalKey, defaultValue) is Float -> sp.getFloat(finalKey, defaultValue) is Boolean -> sp.getBoolean(finalKey, defaultValue) is String -> sp.getString(finalKey, defaultValue) is Set<*> -> sp.getStringSet(finalKey, defaultValue as? Set<String>) else -> throw IllegalStateException("Unsupported type") } as T } override fun setValue(thisRef: Any?, property: KProperty<*>, value: T) { val finalKey = key ?: property.name with(sp.edit()) { when (value) { is Int -> putInt(finalKey, value) is Long -> putLong(finalKey, value) is Float -> putFloat(finalKey, value) is Boolean -> putBoolean(finalKey, value) is String -> putString(finalKey, value) is Set<*> -> putStringSet(finalKey, value.map { it.toString() }.toHashSet()) else -> throw IllegalStateException("Unsupported type") } apply() } }}
使用它:
class CommonPreferences(context: Context) { companion object { /** * 通过传入不同的SP文件名来存储到不同的XML中 */ const val FIR_SP_NAME = "FIR_SP_NAME" //文件名1 const val SEC_SP_NAME = "SEC_SP_NAME"//文件名2 } var isShow by SharedPreferencesDelegate(context, FIR_SP_NAME, false, "key_is_show") //这里没有用key值,则会默认使用属性名来当做key值 var name by SharedPreferencesDelegate(context, FIR_SP_NAME, "") var age by SharedPreferencesDelegate(context, SEC_SP_NAME, 0, "key_age") //这里没有用key值,则会默认使用属性名来当做key值 var cost by SharedPreferencesDelegate(context, SEC_SP_NAME, 0.0f)}
上述代码展示了根据不同的文件名把数据存入到不同的XML文件中,你可以根据自己的需求进行调整。在 Activity 中进行存取值:
private val spInfo = CommonPreferences(this)//存值spInfo.isShow = truespInfo.name = "小马快跑"//存值spInfo.age = 18spInfo.cost = 123.4fspInfo.setString = setOf("一", "二", "三")//取值log("isShow -> ${spInfo.isShow}, name -> ${spInfo.name}")log("age -> ${spInfo.age}, cost -> ${spInfo.cost},setString -> ${spInfo.setString}")
可以看到对sp 的存取值简直不要太简单,跟对象属性的存取似的,来看执行结果:
E/TTT: isShow -> true, name -> 小马快跑E/TTT: age -> 18, cost -> 123.4,setString -> [一, 三, 二]
取值成功了,那么存值呢?看下手机对应目录下是否有存入的数据:
嗯,存取值都成功了。
主要利用的是属性委托val/var <属性名>: <类型> by <表达式>,例如:
var isShow by SharedPreferencesDelegate(context, FIR_SP_NAME, false, "key_is_show")
通过属性代码执行到 SharedPreferencesDelegate 中的逻辑进行存取操作,不必再关心整个的存取细节,nice!
阅读量:822
点赞量:0
收藏量:0