日本搞逼视频_黄色一级片免费在线观看_色99久久_性明星video另类hd_欧美77_综合在线视频

國(guó)內(nèi)最全I(xiàn)T社區(qū)平臺(tái) 聯(lián)系我們 | 收藏本站
阿里云優(yōu)惠2
您當(dāng)前位置:首頁(yè) > php開(kāi)源 > 綜合技術(shù) > 一個(gè)高大上的SharedPreferences工具類——XPrefs

一個(gè)高大上的SharedPreferences工具類——XPrefs

來(lái)源:程序員人生   發(fā)布時(shí)間:2016-07-07 13:52:39 閱讀次數(shù):2538次

背景

SharedPreferences經(jīng)常使用來(lái)存儲(chǔ)1些輕量級(jí)的數(shù)據(jù),SharedPreferences存儲(chǔ)的就是1個(gè)key-value(鍵值對(duì))。Sharedpreferences在平常的android開(kāi)發(fā)中使用的應(yīng)當(dāng)算是挺頻繁的,通常我們開(kāi)發(fā)者為了存儲(chǔ)1個(gè)key,都會(huì)在1個(gè)類里寫好對(duì)應(yīng)的getter和setter方法,而且還要手動(dòng)寫key,也就是說(shuō)寫了方法還要定義key。項(xiàng)目寫的多了以后明顯會(huì)感覺(jué)到這樣寫很麻煩。這時(shí)候候XPrefs就出現(xiàn)了,并很好的解決了這個(gè)問(wèn)題。

XPrefs可以直接保存和讀取實(shí)例對(duì)象,是SharedPreferences中的ORM,還可以通過(guò)接口來(lái)做文章,這類方式用起來(lái)是最方便的,具體介紹接著往下看。

用法

初始化

XPrefs.bind(this);

初始化是綁定了contenxt,以后的操作就不需要傳入context參數(shù)了,如果你傳入activity,會(huì)自動(dòng)轉(zhuǎn)成application context,這樣就避免了內(nèi)存泄漏的問(wèn)題,固然你也能夠在application的類里進(jìn)行綁定操作。

整存整取

/** * 整存整取,把javabean類中的所有有效的字段都寫入sharedpreferences中 */ private void saveAll() { //如果想切換寫入的sharedpreferences文件,可以調(diào)用 // XPrefs.changeFileName("your custom sp file's name"); //如果設(shè)置Mode,如果調(diào)用了changeFileName方法,則必須在changeFileName以后調(diào)用 // XPrefs.changeFileMode(Context.MODE_PRIVATE); //或直接調(diào)用 // XPrefs.changeFileNameAndMode("your custom sp file's name", Context.MODE_PRIVATE); XPrefs.changeFileName(spFile1); UserBean userBean = new UserBean(); userBean.setAge(21); userBean.setFuns(1000); userBean.setMoney(100); userBean.setName("韓梅梅"); userBean.setVIP(true); XPrefs.saveAll(userBean); //讀取,查看存入的數(shù)據(jù) userBean = XPrefs.get(UserBean.class); LogUtils.i("saveAll " + userBean); }

上面代碼中的changeFileName和changeFileMode方法分別是設(shè)置Sharedpreferences文件的name和mode的,要注意的是,如果調(diào)用了changeFileName,那末需要調(diào)用changeFileMode的話就必須要在changeFileName以后調(diào)用。如果不設(shè)置name,默許操作的文件名是XPrefs,默許的mode是Context.MODE_PRIVATE。

接著new了1個(gè)UserBean的實(shí)例,給需要保存的屬性設(shè)置了對(duì)應(yīng)的值,然后調(diào)用saveAll就把UserBean中所有的屬性都保存進(jìn)了SharedPreferences文件里,其中key是屬性名,value是屬性的值。讓我們接著看看UserBean這個(gè)類,

/** * final 修飾的字段不會(huì)被存儲(chǔ) */ private final String InvalidField="InvalidField"; /** * 添加了XIgnore注解的字段會(huì)被忽視,也不會(huì)被存儲(chǔ) */ @XIgnore private String IgnoreField="IgnoreField"; //目前支持以下幾種類型的數(shù)據(jù)存儲(chǔ) private String name; private float money; private int age; private boolean isVIP; private long funs; ...省略1些getter、setter方法和toString()...

用final修飾的屬性和加上@XIgnore注解的屬性都是被疏忽的,不會(huì)被存儲(chǔ)的。存儲(chǔ)的時(shí)候,key是屬性名(如”name”,”money”,”age”…),value是屬性的值。最后通過(guò)下面這行代碼讀取所有存入的數(shù)據(jù),直接調(diào)用userbean的getter方法,就能夠使用這些數(shù)據(jù)。
userBean = XPrefs.get(UserBean.class);
整存整取的好處除方便之外,就是效力高,不管存儲(chǔ)了多少屬性,都只操作了1次文件,有點(diǎn)類似于數(shù)據(jù)庫(kù)中的事物。

既然可以保存和讀取全部javaBean,那末也應(yīng)當(dāng)可以對(duì)javaBean中的單個(gè)屬性進(jìn)行存儲(chǔ)和讀取。

單個(gè)字段的存儲(chǔ)和讀取

/** * 單個(gè)字段的存儲(chǔ)和讀取 */ public void save() { //修改存儲(chǔ)的sharedpreferences文件,mode默許為Context.MODE_PRIVATE XPrefs.changeFileName(spFile2); UserBean userBean = new UserBean(); userBean.setAge(42); userBean.setFuns(2000); userBean.setMoney(200); userBean.setName("李雷"); userBean.setVIP(false); XPrefs.save(userBean, "name"); XPrefs.save(userBean, "age"); XPrefs.save(userBean, "funs"); XPrefs.save(userBean, "money"); XPrefs.save(userBean, "isVIP"); //讀取,查看存入的數(shù)據(jù) Class cls = UserBean.class; boolean isVIP = XPrefs.getBoolean(cls, "isVIP"); String name = XPrefs.getString(cls, "name"); int age = XPrefs.getInt(cls, "age"); long funs = XPrefs.getLong(cls, "funs"); float money = XPrefs.getFloat(cls, "money"); LogUtils.i("save name=" + name + ";money=" + money + ";age=" + age + ";funs=" + funs + ";isVIP=" + isVIP); //整取 userBean = XPrefs.get(UserBean.class); LogUtils.i("save " + userBean.toString()); }

上面的代碼演示了對(duì)UserBean中的字段單獨(dú)進(jìn)行讀寫操作。

XPrefs.save(userBean, "name"); String name = XPrefs.getString(cls, "name");

要注意的save和getString方法傳入的第2個(gè)參數(shù)得和屬性名相同,才能到達(dá)想要的效果。也就是如果定義了1個(gè)屬性private String name;那末傳入的就得是“name”。看上去有點(diǎn)麻煩,確切挺麻煩的,但這只是1種用法,更方便的用法后面會(huì)介紹。

使用接口和注解

private void saveAllAndFollowYourHeart() { IUser user = XPrefs.getObject(IUser.class); user.setName("Tom"); user.setAge(18); user.setFuns(4000); user.setMoney(40000); user.setVip(true); LogUtils.i("IUser name=" + user.getName() + ";money=" + user.getMoney() + ";age=" + user.getAge()+ ";funs=" + user.getFuns() + ";isVIP=" + user.getVip()); }

首先,調(diào)用了XPrefs.getObject(IUser.class)拿到了接口IUser的1個(gè)實(shí)例對(duì)象user,接著分別調(diào)用了user的set和get方法,看上去沒(méi)甚么,但是,在履行set方法的時(shí)候就已把數(shù)據(jù) 存了起來(lái),履行g(shù)et方法就是把數(shù)據(jù)讀取出來(lái)。
具體讓我們看看IUser接口,

@XSPFile(fileName = "IUser", fileMode = Context.MODE_PRIVATE) public interface IUser { @XSet(key = "name", fileName = "IUser", fileMode = Context.MODE_PRIVATE) void setName(String name); @XGet(key = "name") String getName(); @XSet(key = "age") void setAge(int age); @XGet(key = "age") int getAge(); @XSet(key = "funs") void setFuns(int funs); @XGet(key = "funs") int getFuns(); @XSet(key = "vip") void setVip(boolean vip); @XGet(key = "vip") boolean getVip(); @XSet(key = "money") void setMoney(float money); @XGet(key = "money") float getMoney(); }

有3個(gè)注解XSPFile,XSet和XGet,這3個(gè)注解都不是必須的。其中XSPFile是用來(lái)指定file name和mode的,用來(lái)標(biāo)記接口,作用域是類。

@XSPFile(fileName = "IUser", fileMode = Context.MODE_PRIVATE)

XSet和XGet則是來(lái)標(biāo)記方法的作用的,1個(gè)方法用XSet標(biāo)記了,那末這個(gè)方法的作用就是寫入數(shù)據(jù)到指定的SharedPreferences文件中的,其中key就是寫入時(shí)的key。XSet也能指定寫入的文件 name和mode,如果XSPFile和XSet同時(shí)指定了文件的name和mode,那末以XSet指定的為準(zhǔn)。

@XSet(key = "name", fileName = "IUser", fileMode = Context.MODE_PRIVATE) void setName(String name);

如果1個(gè)方法用XGet標(biāo)記了,那末這個(gè)方法的作用就是從SharedPreferences文件中讀取數(shù)據(jù),XGet中的key就是讀取時(shí)的key,其他的和XSet1樣。

@XGet(key = "name") String getName();

這樣也不是很好,每寫1個(gè)方法就得加1個(gè)注解,好麻煩的說(shuō),所以還可以更簡(jiǎn)單點(diǎn)。

使用接口不用注解

private void saveAllAndFollowYourHeartToo() { IEmployee employee = XPrefs.getObject(IEmployee.class); employee.setName("員工"); employee.setAge(22); employee.setSalary(3000); LogUtils.i("IEmployee name=" + employee.getName() + ";age=" + employee.getAge() + ";salary=" + employee.getSalary()); }

這里的用法和用注解的是1樣的,主要還是IEmployee接口上的區(qū)分,

@XSPFile(fileName = "IEmployee", fileMode = Context.MODE_PRIVATE) public interface IEmployee { /** * 存儲(chǔ)字段 name * * @param name value */ void setName(String name); /** * 讀取字段 name * * @return */ String getName(); void setAge(int age); int getAge(); void setSalary(float salary); float getSalary(); }

可以看到,不用注解以后,代碼少了將近1半。
這個(gè)時(shí)候key主要是通過(guò)解析方法名來(lái)得到的,所以1個(gè)方法以set開(kāi)頭的方法的作用就是寫入數(shù)據(jù)到指定的SharedPreferences文件中,其中key就是方法名除去set的后半部份,且首字母小寫,舉個(gè)例子,方法setName的key就是name;
那末1個(gè)以get開(kāi)頭的方法的作用也是很明顯了,就是從SharedPreferences文件中讀取數(shù)據(jù),其中key就是方法名出去get的后半部份,首字母也是小寫,舉個(gè)例子,方法getName的key就是name。看上去已很方便了,但是這都不算甚么,更騷的在后面。

最后1種用法

private void saveAllAndFollowYourHeartThree() { IStudent student = XPrefs.getObject(IStudent.class); student.name("學(xué)生3號(hào)"); student.score(100); student.sex("女"); LogUtils.i("IStudent name=" + student.name() + ";score=" + student.score() + ";sex=" + student.sex()); }

這里的用法和上面兩種仍然沒(méi)有甚么區(qū)分,主要的區(qū)分還是在IStudent接口上,

@XSPFile(fileName = "IStudent") public interface IStudent { /** * 存儲(chǔ)字段 name * * @param name value */ void name(String name); /** * 讀取字段 name * * @return */ String name(); void score(int score); int score(); void sex(String sex); String sex(); }

和上種用法相比,區(qū)分就是方法名中沒(méi)有了set和get,那末這是怎樣判斷方法的作用和要存入數(shù)據(jù)的key的呢?首先,key就是方法名,完完全全的懶人的寫法;其次,方法的作用是通過(guò)方法參數(shù)和方法返回值來(lái)判斷的,

  1. 如果1個(gè)方法有1個(gè)參數(shù),那末這個(gè)方法的作用就是寫入數(shù)據(jù)到指定的SharedPreferences文件中,key是方法名,值是傳入的參數(shù);
  2. 如果1個(gè)方法沒(méi)有參數(shù)并且方法的返回值不是void,那末這個(gè)方法的作用就是從指定的SharedPreferences文件中讀取數(shù)據(jù),key是方法名。

這幾種通過(guò)接口來(lái)做文章的寫法,XPrefs內(nèi)部是通過(guò)動(dòng)態(tài)代理來(lái)做的,java對(duì)動(dòng)態(tài)代理的支持僅限于接口,所以用的是接口,如果不用接口的話就得引入第3方的庫(kù),這類我也做過(guò),但是項(xiàng)目的體積就會(huì)變得更大,終究我放棄了。

混淆注意事項(xiàng)

  • 不要混淆XPrefs中的注解類型,添加混淆配置:
-keep class * extends java.lang.annotation.Annotation { *; }
  • 對(duì)用于持久化的實(shí)體類不要混淆,包括javaBean和接口,在demo中是這樣的:
-keep interface com.huxq17.xprefs.example.interfaces.** { *; } -keepclasseswithmembers class com.huxq17.xprefs.example.UserBean { <fields>; <methods>; }

具體根據(jù)自己項(xiàng)目情況而定。

最后

XPrefs的地址:點(diǎn)擊我,這次這個(gè)項(xiàng)目的靈感來(lái)源于github上的1個(gè)項(xiàng)目,當(dāng)時(shí)我就在思考怎樣做出1個(gè)簡(jiǎn)單易用的SharedPreferences工具類,為了尋覓靈感我就在github上面亂逛,1次偶然的機(jī)會(huì)我看到了這個(gè)項(xiàng)目,瀏覽了項(xiàng)目里的代碼,思路立馬就清晰了,項(xiàng)目地址:androidInject,非常感謝這個(gè)項(xiàng)目的作者。

生活不易,碼農(nóng)辛苦
如果您覺(jué)得本網(wǎng)站對(duì)您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈(zèng)
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關(guān)閉
程序員人生
主站蜘蛛池模板: 成人av在线网 | 让男人欲仙欲死的床技 | 亚洲精品久久久久久一区二区 | 99爱在线视频 | 不卡中文一区 | 日韩精品在线看 | 91色在线视频 | 黄色一级毛片 | 国产一区不卡 | 久久久蜜臀 | 亚洲日韩中文字幕一区 | 这里精品 | 日日草视频 | 日韩a级毛片免费看 | 亚洲国产精品99久久久久久久久 | 一区二区三区四区在线视频 | 91精品福利 | 久久免费99精品久久久久久 | 久久久久久久久久一区二区 | 亚洲欧美激情视频 | 范冰冰一级做a爰片久久毛片 | 男女的隐私视频网站 | 99精品欧美一区二区三区 | 黄色国产大片 | 日韩不卡在线 | 国产欧美日韩综合 | 欧美精品在线免费观看 | 国外成人在线视频网站 | 欧美91视频| 成人性生交大片免费观看嘿嘿视频 | 在线成人 | 久久久福利视频 | 99久久综合 | 在线视频国产一区 | 黄色裸体网站 | 欧美一区二区免费视频 | 久久国产视频播放 | 成人av激情| 中文字幕亚洲专区 | 国产综合久久 | 亚洲 欧美 综合 |