将SparseBooleanArray保存到SharedPreferences

3

对于我的应用程序,我需要将一个简单的SparseBooleanArray保存到内存中并在以后读取它。是否有办法使用SharedPreferences保存它?

我考虑过使用SQLite数据库,但对于这么简单的东西来说,它似乎太过复杂了。我在StackOverflow上找到了一些其他答案,建议使用GSON将其保存为字符串,但我需要使此应用程序在文件大小方面非常轻便和快速。有没有办法在不依赖第三方库的情况下实现这一点,并保持良好的性能?

4个回答

5
您可以利用JSON的强大功能,将任何类型的对象保存在共享首选项中。
例如,SparseIntArray可以像Json字符串一样保存项目。
public static void saveArrayPref(Context context, String prefKey, SparseIntArray intDict) {
    SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
    SharedPreferences.Editor editor = prefs.edit();
    JSONArray json = new JSONArray();
    StringBuffer data = new StringBuffer().append("[");
    for(int i = 0; i < intDict.size(); i++) {
        data.append("{")
                .append("\"key\": ")
                .append(intDict.keyAt(i)).append(",")
                .append("\"order\": ")
                .append(intDict.valueAt(i))
                .append("},");
        json.put(data);
    }
    data.append("]");
    editor.putString(prefKey, intDict.size() == 0 ? null : data.toString());
    editor.commit();
}

以及阅读JSON字符串

public static SparseIntArray getArrayPref(Context context, String prefKey) {
    SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
    String json = prefs.getString(prefKey, null);
    SparseIntArray intDict = new SparseIntArray();
    if (json != null) {
        try {
            JSONArray jsonArray = new JSONArray(json);
            for (int i = 0; i < jsonArray.length(); i++) {
                JSONObject item = jsonArray.getJSONObject(i);
                intDict.put(item.getInt("key"), item.getInt("order"));
            }
        } catch (JSONException e) {
            e.printStackTrace();
        }
    }
    return intDict;
}

并且可以这样使用:
    SparseIntArray myKeyList = new SparseIntArray(); 
    ...
    //write list
    saveArrayPref(getApplicationContext(),"MyList", myKeyList);
    ...
    //read list
    myKeyList = getArrayPref(getApplicationContext(), "MyList");

聪明!我喜欢它! - Pkmmte

3
将值分开写,并保留所写值的名称列表:
    SparseBooleanArray array = //your array;
    SharedPreferences prefs = //your preferences

    //write
    SharedPreferences.Editor edit = prefs.edit();
    Set<String> keys = new HashSet<String>(array.size());
    for(int i = 0, z = array.size(); i < z; ++i) {
        int key = array.keyAt(i);
        keys.add(String.valueOf(key));
        edit.putBoolean("key_" + key, array.valueAt(i));
    }
    edit.putStringSet("keys", keys);
    edit.commit();

    //read
    Set<String> set = prefs.getStringSet("keys", null);
    if(set != null && !set.isEmpty()) {
        for (String key : set) {
            int k = Integer.parseInt(key);
            array.put(k, prefs.getBoolean("key_"+key, false));
        }
    }

自 API 11 开始支持字符串集合。您可以构建一个单独的 CSV 字符串并拆分它,而不是存储集合。


1
您可以将对象序列化为字节数组,然后在保存到SharedPreferences之前可能对字节数组进行base64编码。对象序列化非常容易,您不需要第三方库来完成。
public static byte[] serialize(Object obj) {
    ByteArrayOutputStream byteArrayOS = new ByteArrayOutputStream();
    ObjectOutputStream objectOS = new ObjectOutputStream(byteArrayOS);
    objectOS.writeObject(obj);
    objectOS.flush();
    return byteArrayOS.toByteArray();
}

public static Object deserialize(byte[] data) {
    ByteArrayInputStream byteArrayIS = new ByteArrayInputStream(data);
    ObjectInputStream objectIS = new ObjectInputStream(byteArrayIS);
    return objectIS.readObject();
}

为了简单起见,上面的代码没有try catch块。您可以自行添加。


这个在性能方面有多好? 另外,我注意到你正在使用一个字节数组。如果没有允许该数据类型的方法,我应该如何将该字节数组保存到SharedPreferences中? - Pkmmte
任何形式的序列化都很慢。但是,除非您的对象达到了几兆字节或更大,否则延迟实际上是非常不明显的。据我所理解,您只需要保存一个数组。我想这应该没问题。 - Krypton
在保存之前,你需要将字节数组进行Base64编码,将其转换为字符串。然后在读取并反序列化之前,你需要进行解码,将字符串还原为字节数组。 - Krypton

0

我已经使用 Gson 进行以下操作:

在 SharedPreference 中保存 SparseBooleanArray:

public void SaveSparseBoolean() {
    SparseBooleanArray booleanArray = new SparseBooleanArray();
    SharedPreferences sP;
    sP=context.getSharedPreferences("MY_APPS_PREF",Context.MODE_PRIVATE)
    SharedPreferences.Editor editor=sP.edit();
    Gson gson=new Gson();
    editor.putString("Sparse_Array",gson.toJson(booleanArray));
    editor.commit();
}

从SharedPreferences获取SparsebooleanArray
public SparseBooleanArray getSparseArray() {
    SparseBooleanArray booleanArray;
    SharedPreferences sP;
    sP = context.getSharedPreferences("MY_APPS_PREF", Context.MODE_PRIVATE);
    Gson gson=new Gson();
    booleanArray=gson.fromJson(sP.getString("Sparse_Array",""),SparseBooleanArray.class);
    return booleanArray;

}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接