性能優(yōu)化是一條漫長的路席揽,走著走著就迷了路,一直走,一直迷...
小小簡介
SharedPreference是Android系統(tǒng)中一種簡單的、輕量級的文件存儲窥摄,它是一種持久化的存儲方式抑片,以名稱/值對(NVP)機制存放在xml中map根標(biāo)簽下,正如其名无虚,它比較適合一些簡單數(shù)據(jù)的存儲,用于保存Int、long聂宾、boolean、String诊笤、Float系谐、Set這些數(shù)據(jù)類型,可以在data/data/應(yīng)用程序/shared_prefs的目錄下可以查找到保存的xml文件讨跟。
基本使用方式
- 獲取SharedPreference對象
SharedPreferences sp = context.getSharedPreferences(PREFERENCES_NAME,Context.MODE_PRIVATE);
- 獲取 SharedPreferences.Editor
SharedPreferences.Editor edit = sp.edit();
- 存儲數(shù)據(jù)
edit.putString(String key,String value);
edit.putStringSet(String key, Set<String> values);
edit.putLong(String key,long value);
edit.putFloat(String key,float value);
edit.putBoolean(String key,boolean value);
edit.putInt(String key,int value);
edit.commit();//同步寫入纪他,頻繁讀取會阻塞主線程,引起ANR
edit.apply();//異步寫入晾匠,不關(guān)心結(jié)果茶袒,官方推薦,速度與性能較好
- 獲取數(shù)據(jù)
sp.getString(String key,String value);
sp.getStringSet(String key, Set<String> values);
sp.getLong(String key,long value);
sp.getFloat(String key,float value);
sp.getBoolean(String key,boolean value);
sp.getInt(String key,int value);
這些基本使用方式應(yīng)該不用啰嗦去介紹了凉馆,本文主要談一些SP存儲上的優(yōu)化建議??薪寓,下圖為自己在SP讀寫性能上的測試乾巧,僅供參考:
耗時統(tǒng)計
存儲方式 | 數(shù)據(jù)條數(shù) | 耗時/ms |
---|---|---|
多次commit | 1000 | 15052 |
一次性commit | 1000 | 24 |
多次apply | 1000 | 588 |
一次性apply | 1000 | 12 |
json | 1000 | 73 |
從耗時統(tǒng)計上看,在操作上预愤,明顯能看出頻繁執(zhí)行commit與apply操作是非常耗時的沟于,那么卡頓的解決方案也呼之而出;在使用上植康,使用commit與apply的區(qū)別旷太,雖然都是保存數(shù)據(jù),但是在性能和耗時上也略顯不同销睁;在數(shù)據(jù)格式上供璧,json文件與簡單的KV數(shù)據(jù)性能上的差別。下面是結(jié)合這個測試結(jié)果給出的一些建議:
關(guān)于優(yōu)化的建議
- 建議在Application中初始化冻记,重寫attachBaseContext()睡毒,參數(shù)context直接傳入Application對象即可。
- 最好使用單例冗栗,不必每次都從系統(tǒng)獲取Sp對象演顾,減少開銷。
- 如果項目中使用了MultiDex隅居,存在分包钠至,請在分包前即MultiDex.install()之前或者在multidex執(zhí)行的這段時間初始化。因為這時cpu是利用不滿的胎源,我們沒有辦法充分利用CPU的原因棉钧,是因為如果我們在Multidex之前執(zhí)行一些操作,我們很有可能因為這樣一些操作的類或者是相關(guān)的類不在我們的主dex當(dāng)中涕蚤,在四點幾版本中會直接崩潰宪卿,但是由于sharePreference不會產(chǎn)生這種崩潰,它是系統(tǒng)的類万栅。
- 請不要使用SharedPreference存儲大文件及存儲大量的key和value佑钾,這樣的話會造成界面卡頓或者ANR比較占內(nèi)存,記住它是簡單存儲申钩,如果有類似的需求請考慮數(shù)據(jù)庫次绘、磁盤文件存儲等等瘪阁。
- 推薦使用apply進(jìn)行存儲撒遣,這也是官方推薦,當(dāng)讀入內(nèi)存后管跺,因為它是異步寫入磁盤的义黎,所以效率上會比commit好,如果你需要存儲狀態(tài)或者即存即用的話還是盡量使用commit豁跑。
- 請不要頻繁使用apply與commit廉涕,如果存在這樣的問題,請合并一次性apply與commit,可以參考封裝一個map的結(jié)合,一次性提交狐蜕,因為SharedPreference可能會存在IO瓶頸和鎖性能差的問題宠纯。
- 盡量不要存放Json及html,數(shù)據(jù)少可以层释,無需擔(dān)心婆瓜,大量的話請放棄。
- 不要所有的數(shù)據(jù)都存在一個文件贡羔,不同類型的文件或者數(shù)據(jù)可以分開多個文件存儲廉白,避免使用一個大文件,這樣可提高讀取速度乖寒。
- 跨進(jìn)程操作不要使用MULTI_PROCESS標(biāo)志猴蹂,而是使用contentprovide等進(jìn)程間通信的方式。
- 如果你的項目對于存儲性能要求非常高的情況楣嘁,可以考慮放棄系統(tǒng)的SP存儲磅轻,推薦你使用騰訊的高性能組件MMKV,目前超過8.8k+的star逐虚。
SP工具類
封裝是基于AndroidUtilCode進(jìn)行的部分改造瓢省,增加了提交Map的操作,方便一次性commit與apply痊班,操作時請直接使用SpHelpUtils輔助類勤婚,需要的話直接復(fù)制+粘貼,減少跳轉(zhuǎn)GitHub的時間涤伐,程序員就應(yīng)該懶到極致馒胆。
/**
* description:SpUtils工具類的封裝類(使用前,請在相應(yīng)app的Applicaiton中初始化凝果,傳入getApplicationContext())
*/
public class SpHelpUtils {
/**
* 簡單存儲工具類
*/
private static SpUtils sDefaultSpUtils;
/**
* Set the default instance of {@link SpUtils}.
*
* @param spUtils The default instance of {@link SpUtils}.
*/
public static void setDefaultSpUtils(final SpUtils spUtils) {
sDefaultSpUtils = spUtils;
}
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final String value) {
put(key, value, getDefaultSpUtils());
}
/**
* 提交map,一次性commit,減少頻繁讀寫IO
*
* @param hashmap 存儲集合
*/
public static void put(@NotNull final Map<String, Object> hashmap) {
put(hashmap, getDefaultSpUtils());
}
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key, final String value, final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* 提交map,一次性commit,減少頻繁讀寫IO
*
* @param hashmap 存儲集合
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(final Map<String, Object> hashmap, final boolean isCommit) {
put(hashmap, isCommit, getDefaultSpUtils());
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @return the string value if sp exists or {@code ""} otherwise
*/
public static String getString(@NonNull final String key) {
return getString(key, getDefaultSpUtils());
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the string value if sp exists or {@code defaultValue} otherwise
*/
public static String getString(@NonNull final String key, final String defaultValue) {
return getString(key, defaultValue, getDefaultSpUtils());
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final int value) {
put(key, value, getDefaultSpUtils());
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key, final int value, final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @return the int value if sp exists or {@code -1} otherwise
*/
public static int getInt(@NonNull final String key) {
return getInt(key, getDefaultSpUtils());
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the int value if sp exists or {@code defaultValue} otherwise
*/
public static int getInt(@NonNull final String key, final int defaultValue) {
return getInt(key, defaultValue, getDefaultSpUtils());
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final long value) {
put(key, value, getDefaultSpUtils());
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key, final long value, final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @return the long value if sp exists or {@code -1} otherwise
*/
public static long getLong(@NonNull final String key) {
return getLong(key, getDefaultSpUtils());
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the long value if sp exists or {@code defaultValue} otherwise
*/
public static long getLong(@NonNull final String key, final long defaultValue) {
return getLong(key, defaultValue, getDefaultSpUtils());
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final float value) {
put(key, value, getDefaultSpUtils());
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key, final float value, final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @return the float value if sp exists or {@code -1f} otherwise
*/
public static float getFloat(@NonNull final String key) {
return getFloat(key, getDefaultSpUtils());
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the float value if sp exists or {@code defaultValue} otherwise
*/
public static float getFloat(@NonNull final String key, final float defaultValue) {
return getFloat(key, defaultValue, getDefaultSpUtils());
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final boolean value) {
put(key, value, getDefaultSpUtils());
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key, final boolean value, final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @return the boolean value if sp exists or {@code false} otherwise
*/
public static boolean getBoolean(@NonNull final String key) {
return getBoolean(key, getDefaultSpUtils());
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the boolean value if sp exists or {@code defaultValue} otherwise
*/
public static boolean getBoolean(@NonNull final String key, final boolean defaultValue) {
return getBoolean(key, defaultValue, getDefaultSpUtils());
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public static void put(@NonNull final String key, final Set<String> value) {
put(key, value, getDefaultSpUtils());
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void put(@NonNull final String key,
final Set<String> value,
final boolean isCommit) {
put(key, value, isCommit, getDefaultSpUtils());
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @return the set of string value if sp exists
* or {@code Collections.<String>emptySet()} otherwise
*/
public static Set<String> getStringSet(@NonNull final String key) {
return getStringSet(key, getDefaultSpUtils());
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the set of string value if sp exists or {@code defaultValue} otherwise
*/
public static Set<String> getStringSet(@NonNull final String key,
final Set<String> defaultValue) {
return getStringSet(key, defaultValue, getDefaultSpUtils());
}
/**
* Return all values in sp.
*
* @return all values in sp
*/
public static Map<String, ?> getAll() {
return getAll(getDefaultSpUtils());
}
/**
* Return whether the sp contains the preference.
*
* @param key The key of sp.
* @return {@code true}: yes<br>{@code false}: no
*/
public static boolean contains(@NonNull final String key) {
return contains(key, getDefaultSpUtils());
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
*/
public static void remove(@NonNull final String key) {
remove(key, getDefaultSpUtils());
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void remove(@NonNull final String key, final boolean isCommit) {
remove(key, isCommit, getDefaultSpUtils());
}
/**
* Remove all preferences in sp.
*/
public static void clear() {
clear(getDefaultSpUtils());
}
/**
* Remove all preferences in sp.
*
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public static void clear(final boolean isCommit) {
clear(isCommit, getDefaultSpUtils());
}
///////////////////////////////////////////////////////////////////////////
// dividing line
///////////////////////////////////////////////////////////////////////////
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final String value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* 一次性提交
*
* @param map 存儲集合
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final Map<String, Object> map, @NonNull final SpUtils spUtils) {
spUtils.put(map);
}
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final String value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* 一次性提交
*
* @param map 存儲集合
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final Map<String, Object> map, final boolean isCommit, @NonNull final SpUtils spUtils) {
spUtils.put(map, isCommit);
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the string value if sp exists or {@code ""} otherwise
*/
public static String getString(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getString(key);
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the string value if sp exists or {@code defaultValue} otherwise
*/
public static String getString(@NonNull final String key,
final String defaultValue,
@NonNull final SpUtils spUtils) {
return spUtils.getString(key, defaultValue);
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final int value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final int value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the int value if sp exists or {@code -1} otherwise
*/
public static int getInt(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getInt(key);
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the int value if sp exists or {@code defaultValue} otherwise
*/
public static int getInt(@NonNull final String key, final int defaultValue, @NonNull final SpUtils spUtils) {
return spUtils.getInt(key, defaultValue);
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final long value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final long value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the long value if sp exists or {@code -1} otherwise
*/
private static long getLong(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getLong(key);
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the long value if sp exists or {@code defaultValue} otherwise
*/
private static long getLong(@NonNull final String key, final long defaultValue, @NonNull final SpUtils spUtils) {
return spUtils.getLong(key, defaultValue);
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final float value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final float value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the float value if sp exists or {@code -1f} otherwise
*/
private static float getFloat(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getFloat(key);
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the float value if sp exists or {@code defaultValue} otherwise
*/
private static float getFloat(@NonNull final String key, final float defaultValue, @NonNull final SpUtils spUtils) {
return spUtils.getFloat(key, defaultValue);
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final boolean value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final boolean value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the boolean value if sp exists or {@code false} otherwise
*/
public static boolean getBoolean(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getBoolean(key);
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the boolean value if sp exists or {@code defaultValue} otherwise
*/
public static boolean getBoolean(@NonNull final String key,
final boolean defaultValue,
@NonNull final SpUtils spUtils) {
return spUtils.getBoolean(key, defaultValue);
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key, final Set<String> value, @NonNull final SpUtils spUtils) {
spUtils.put(key, value);
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void put(@NonNull final String key,
final Set<String> value,
final boolean isCommit,
@NonNull final SpUtils spUtils) {
spUtils.put(key, value, isCommit);
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return the set of string value if sp exists
* or {@code Collections.<String>emptySet()} otherwise
*/
private static Set<String> getStringSet(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.getStringSet(key);
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @param spUtils The instance of {@link SpUtils}.
* @return the set of string value if sp exists or {@code defaultValue} otherwise
*/
private static Set<String> getStringSet(@NonNull final String key,
final Set<String> defaultValue,
@NonNull final SpUtils spUtils) {
return spUtils.getStringSet(key, defaultValue);
}
/**
* Return all values in sp.
*
* @param spUtils The instance of {@link SpUtils}.
* @return all values in sp
*/
private static Map<String, ?> getAll(@NonNull final SpUtils spUtils) {
return spUtils.getAll();
}
/**
* Return whether the sp contains the preference.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
* @return {@code true}: yes<br>{@code false}: no
*/
public static boolean contains(@NonNull final String key, @NonNull final SpUtils spUtils) {
return spUtils.contains(key);
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
* @param spUtils The instance of {@link SpUtils}.
*/
public static void remove(@NonNull final String key, @NonNull final SpUtils spUtils) {
spUtils.remove(key);
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void remove(@NonNull final String key, final boolean isCommit, @NonNull final SpUtils spUtils) {
spUtils.remove(key, isCommit);
}
/**
* Remove all preferences in sp.
*
* @param spUtils The instance of {@link SpUtils}.
*/
public static void clear(@NonNull final SpUtils spUtils) {
spUtils.clear();
}
/**
* Remove all preferences in sp.
*
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
* @param spUtils The instance of {@link SpUtils}.
*/
public static void clear(final boolean isCommit, @NonNull final SpUtils spUtils) {
spUtils.clear(isCommit);
}
/**
* 獲取簡單存儲工具類 SpUtils
*
* @return SpUtils
*/
private static SpUtils getDefaultSpUtils() {
return sDefaultSpUtils != null ? sDefaultSpUtils : SpUtils.getInstance(getApplicationByReflect());
}
/**
* 如果你沒有初始化該工具類祝迂,那么我會通過反射獲取當(dāng)前的applicationContext()
*
* @return Application
*/
private static Application getApplicationByReflect() {
try {
@SuppressLint("PrivateApi")
Class<?> activityThread = Class.forName("android.app.ActivityThread");
Object thread = activityThread.getMethod("currentActivityThread").invoke(null);
Object app = activityThread.getMethod("getApplication").invoke(thread);
if (app == null) {
throw new NullPointerException("u should init first");
}
return (Application) app;
} catch (NoSuchMethodException | IllegalAccessException | ClassNotFoundException | InvocationTargetException e) {
e.printStackTrace();
}
throw new NullPointerException("u should init first");
}
}
public class SpUtils {
private static final Map<String, SpUtils> SP_UTILS_MAP = new HashMap<>();
private SharedPreferences sp;
/**
* Return the single {@link SpUtils} instance
*
* @param context context
* @return the single {@link SpUtils} instance
*/
public static SpUtils getInstance(Context context) {
return getInstance(context, "", Context.MODE_PRIVATE);
}
/**
* Return the single {@link SpUtils} instance
*
* @param context context
* @param mode Operating mode.
* @return the single {@link SpUtils} instance
*/
public static SpUtils getInstance(Context context, final int mode) {
return getInstance(context, "", mode);
}
/**
* Return the single {@link SpUtils} instance
*
* @param context context
* @param spName The name of sp.
* @return the single {@link SpUtils} instance
*/
public static SpUtils getInstance(Context context, String spName) {
return getInstance(context, spName, Context.MODE_PRIVATE);
}
/**
* Return the single {@link SpUtils} instance
*
* @param context context
* @param spName The name of sp.
* @param mode Operating mode.
* @return the single {@link SpUtils} instance
*/
public static SpUtils getInstance(Context context, String spName, final int mode) {
if (context == null) {
throw new UnsupportedOperationException("context can't empty, please init me in SpHelpUtils.class");
}
if (isSpace(spName)) {
spName = context.getPackageName() + "_preferences";
}
SpUtils spUtils = SP_UTILS_MAP.get(spName);
if (spUtils == null) {
synchronized (SpUtils.class) {
spUtils = SP_UTILS_MAP.get(spName);
if (spUtils == null) {
spUtils = new SpUtils(context, spName, mode);
SP_UTILS_MAP.put(spName, spUtils);
}
}
}
return spUtils;
}
private SpUtils(Context context, final String spName) {
sp = context.getSharedPreferences(spName, Context.MODE_PRIVATE);
}
private SpUtils(final Context context, final String spName, final int mode) {
sp = context.getSharedPreferences(spName, mode);
}
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final String value) {
// TODO 由于項目的功能需求,這個地方標(biāo)志位統(tǒng)一改為走commit方式,后期需要逐一優(yōu)化成apply
put(key, value, true);
}
/**
* 提交Map結(jié)合器净,用于一次性的commit或者apply型雳,減少平凡讀寫IO
*
* @param map 存儲集合
*/
public void put(@NonNull final Map<String, Object> map) {
put(map, true);
}
/**
* Put the string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key, final String value, final boolean isCommit) {
if (isCommit) {
sp.edit().putString(key, value).commit();
} else {
sp.edit().putString(key, value).apply();
}
}
/**
* @param map 存儲集合
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final Map<String, Object> map, final boolean isCommit) {
SharedPreferences.Editor edit = sp.edit();
for (Map.Entry<String, Object> next : map.entrySet()) {
if (next.getValue() instanceof String) {
edit.putString(next.getKey(), String.valueOf(next.getValue()));
} else if (next.getValue() instanceof Boolean) {
edit.putBoolean(next.getKey(), (Boolean) next.getValue());
} else if (next.getValue() instanceof Integer) {
edit.putInt(next.getKey(), (Integer) next.getValue());
} else if (next.getValue() instanceof Float) {
edit.putFloat(next.getKey(), (Float) next.getValue());
} else if (next.getValue() instanceof Long) {
edit.putLong(next.getKey(), (Long) next.getValue());
} else {
throw new UnsupportedOperationException("parameter Unsupported type!");
}
}
if (isCommit) {
edit.commit();
} else {
edit.apply();
}
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @return the string value if sp exists or {@code ""} otherwise
*/
public String getString(@NonNull final String key) {
return getString(key, "");
}
/**
* Return the string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the string value if sp exists or {@code defaultValue} otherwise
*/
public String getString(@NonNull final String key, final String defaultValue) {
return sp.getString(key, defaultValue);
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final int value) {
put(key, value, false);
}
/**
* Put the int value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key, final int value, final boolean isCommit) {
if (isCommit) {
sp.edit().putInt(key, value).commit();
} else {
sp.edit().putInt(key, value).apply();
}
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @return the int value if sp exists or {@code -1} otherwise
*/
public int getInt(@NonNull final String key) {
return getInt(key, -1);
}
/**
* Return the int value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the int value if sp exists or {@code defaultValue} otherwise
*/
public int getInt(@NonNull final String key, final int defaultValue) {
return sp.getInt(key, defaultValue);
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final long value) {
put(key, value, false);
}
/**
* Put the long value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key, final long value, final boolean isCommit) {
if (isCommit) {
sp.edit().putLong(key, value).commit();
} else {
sp.edit().putLong(key, value).apply();
}
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @return the long value if sp exists or {@code -1} otherwise
*/
public long getLong(@NonNull final String key) {
return getLong(key, -1L);
}
/**
* Return the long value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the long value if sp exists or {@code defaultValue} otherwise
*/
public long getLong(@NonNull final String key, final long defaultValue) {
return sp.getLong(key, defaultValue);
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final float value) {
put(key, value, false);
}
/**
* Put the float value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key, final float value, final boolean isCommit) {
if (isCommit) {
sp.edit().putFloat(key, value).commit();
} else {
sp.edit().putFloat(key, value).apply();
}
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @return the float value if sp exists or {@code -1f} otherwise
*/
public float getFloat(@NonNull final String key) {
return getFloat(key, -1f);
}
/**
* Return the float value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the float value if sp exists or {@code defaultValue} otherwise
*/
public float getFloat(@NonNull final String key, final float defaultValue) {
return sp.getFloat(key, defaultValue);
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final boolean value) {
put(key, value, false);
}
/**
* Put the boolean value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key, final boolean value, final boolean isCommit) {
if (isCommit) {
sp.edit().putBoolean(key, value).commit();
} else {
sp.edit().putBoolean(key, value).apply();
}
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @return the boolean value if sp exists or {@code false} otherwise
*/
public boolean getBoolean(@NonNull final String key) {
return getBoolean(key, false);
}
/**
* Return the boolean value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the boolean value if sp exists or {@code defaultValue} otherwise
*/
public boolean getBoolean(@NonNull final String key, final boolean defaultValue) {
return sp.getBoolean(key, defaultValue);
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
*/
public void put(@NonNull final String key, final Set<String> value) {
put(key, value, false);
}
/**
* Put the set of string value in sp.
*
* @param key The key of sp.
* @param value The value of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void put(@NonNull final String key,
final Set<String> value,
final boolean isCommit) {
if (isCommit) {
sp.edit().putStringSet(key, value).commit();
} else {
sp.edit().putStringSet(key, value).apply();
}
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @return the set of string value if sp exists
* or {@code Collections.<String>emptySet()} otherwise
*/
public Set<String> getStringSet(@NonNull final String key) {
return getStringSet(key, Collections.emptySet());
}
/**
* Return the set of string value in sp.
*
* @param key The key of sp.
* @param defaultValue The default value if the sp doesn't exist.
* @return the set of string value if sp exists or {@code defaultValue} otherwise
*/
public Set<String> getStringSet(@NonNull final String key,
final Set<String> defaultValue) {
return sp.getStringSet(key, defaultValue);
}
/**
* Return all values in sp.
*
* @return all values in sp
*/
public Map<String, ?> getAll() {
return sp.getAll();
}
/**
* Return whether the sp contains the preference.
*
* @param key The key of sp.
* @return {@code true}: yes<br>{@code false}: no
*/
public boolean contains(@NonNull final String key) {
return sp.contains(key);
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
*/
public void remove(@NonNull final String key) {
remove(key, false);
}
/**
* Remove the preference in sp.
*
* @param key The key of sp.
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void remove(@NonNull final String key, final boolean isCommit) {
if (isCommit) {
sp.edit().remove(key).commit();
} else {
sp.edit().remove(key).apply();
}
}
/**
* Remove all preferences in sp.
*/
public void clear() {
clear(false);
}
/**
* Remove all preferences in sp.
*
* @param isCommit True to use {@link SharedPreferences.Editor#commit()},
* false to use {@link SharedPreferences.Editor#apply()}
*/
public void clear(final boolean isCommit) {
if (isCommit) {
sp.edit().clear().commit();
} else {
sp.edit().clear().apply();
}
}
private static boolean isSpace(final String s) {
if (s == null) {
return true;
}
for (int i = 0, len = s.length(); i < len; ++i) {
if (!Character.isWhitespace(s.charAt(i))) {
return false;
}
}
return true;
}
}
寫在最后
感謝各位大佬的閱讀,如果存在不足的地方或者有更好的建議山害,請留言回復(fù)纠俭,我會盡量把文章的質(zhì)量做到更好以分享給更多的讀者,謝謝浪慌!