I have a problem with storing string set preference. I have these utility methods for storing:
public static void putStringSet(SharedPreferences pref, Editor e, String key, Set<String> set)
{
if (Utils.isApiLevelGreaterThanGingerbread())
{
// e.remove(key); // I tried to remove it here
e.putStringSet(key, set);
}
else
{
// removes old occurences of key
for (String k : pref.getAll().keySet())
{
if (k.startsWith(key))
{
e.remove(k);
}
}
int i = 0;
for (String value : set)
{
e.putString(key + i++, value);
}
}
}
public static Set<String> getStringSet(SharedPreferences pref, String key, Set<String> defaultValue)
{
if (Utils.isApiLevelGreaterThanGingerbread())
{
return pref.getStringSet(key, defaultValue);
}
else
{
Set<String> set = new HashSet<String>();
int i = 0;
Set<String> keySet = pref.getAll().keySet();
while (keySet.contains(key + i))
{
set.add(pref.getString(key + i, ""));
i++;
}
if (set.isEmpty())
{
return defaultValue;
}
else
{
return set;
}
}
}
I use these methods to be backward compatible with GB. But I have a problem that using putStringSet method isn't persistent for API > gingerbread. It is persistent while app is runing. But it dissapears after restart. I will describe the steps:
- Clean install of application - there is no preference with key X
- I store string set A with key X - preference contains A
- I store string set B with key X - preference contains B
- Close app
- Restart of app - preference contains A
- I store string set C with key X - preference contains C
- Close app
- Restart of app - preference contains A
So only the first value is persistent and I cannot overwrite it.
Other notes:
- this methods just replaces putStringSet and getStringSet. So I use commit()...but elsewhere (see example below).
- I tried to replace commit() with apply() - no success
- When I use code for older APIs in newer APIs (I commented first 4 lines in both methods) it works flawlessly but it isn't so efficient
Example of use:
Editor e = mPref.edit();
PreferencesUtils.putStringSet(mPref, e, GlobalPreferences.INCLUDED_DIRECTORIES, dirs);
e.commit();
Thnak you very much for help.
This has a ridiculous amount of duplicates - I bet that you do :
set = prefs.getStringSet("X", new HashSet<String>());
set.add("yada yada");
prefs.putStringSet("X", set);
In short android sees that set and the one inside refer to the same set and does nothing. Correct ?
See: Misbehavior when trying to store a string set using SharedPreferences
My condition is very similar to yours, the only difference is when restart the app, preference contains A, B, C, but when reinstall it or reboot the phone, B&C are gone.
I also tried replace commit() with apply(), as this post adviced SharedPreferences not persistent , but still not to work.
I solved this problem by remove & commit the preference before replacing it:
editor.remove("StringSetKey");
editor.commit();
editor.putStringSet("StringSetKey", newSet);
editor.commit();
Ps: you can type adb pull /data/data/<packagename>/shared_prefs/xxxx.xml
in cmd line to see if the commit() really works
Pps: I think this is a bug with putStringSet....
hope this will help you ;)
来源:https://stackoverflow.com/questions/16820252/android-string-set-preference-is-not-persistent