別人寫的黑滴,寫的不錯,收藏一波
1:KVC? ? 2:runTime字典轉(zhuǎn)模型
先說說兩種的不同:KVC是遍歷字典中的key值逆屡,去模型類里面去查找有沒有所對應(yīng)的key前鹅,runtime反之是遍歷屬性在字典里面去查找有沒有對應(yīng)的key,在實(shí)際開發(fā)中碌识,因?yàn)楹笈_返回的數(shù)據(jù)比較多碾篡,可用的字段就比較少,所以用runtime效率較高筏餐。
KVC原理:鍵值編碼是用來間接訪問對象屬性的機(jī)制开泽,通過setValue:forKey和ValueForkey來訪問成員變量,代碼量比較少使用比較簡單魁瞪。
使用方法:
1.創(chuàng)建一個Model類穆律,在.h里面聲明兩個方法,并且聲明需要的屬性(可以參照我寫的自動聲明屬性去完成這個步驟)
- (instancetype)initWithDictionary:(NSDictionary *)dict;
+ (instancetype)provinceWithDictionary:(NSDictionary *)dict;
2.在.m里面去實(shí)現(xiàn)
- (instancetype)initWithDictionary:(NSDictionary *)dict
{
if (self = [super init]) {
[self setValuesForKeysWithDictionary:dict];
}
return self;
}
+ (instancetype)provinceWithDictionary:(NSDictionary *)dict
{
return [[self alloc] initWithDictionary:dict];
}
3.在這里我們直接可以在ViewController里面調(diào)這個方法
VisitorModel *model = [VisitorModel provinceWithDictionary:temDic];就完成了賦值了
注意:我們在使用KVC過程中因?yàn)槭峭ㄟ^字典去在你模型類里面去查找有沒有這個屬性:或者字典里面有關(guān)鍵字:程序會拋出異常导俘,這里我們要玩成一個方法:
-(void)setValue:(id)value forUndefinedKey:(NSString *)key{
}
這個寫著就沒事了峦耘,如果是id類型,我們先聲明一個ID屬性旅薄,然后給它賦值辅髓。
KVC的使用就介紹這么多,使用起來也是很方便的少梁。
第二種:runtime字典轉(zhuǎn)模型
先說說一級的字典轉(zhuǎn)模型
步驟1.首先創(chuàng)建一個model類還是通過我封裝的自動聲明屬性洛口,然后把輸出的粘貼到.h里面
步驟2:直接調(diào)用我這封裝的就可以了,封裝內(nèi)部的原理如下
1.創(chuàng)建一個分類 NSObject (model)
2猎莲,在.h里面寫一個方法
+(instancetype)modelWithDic:(NSDictionary*)dict;只需要傳入一個字典就會自動轉(zhuǎn)模型的
3.在.m里面實(shí)現(xiàn)方法
+(instancetype)modelWithDic:(NSDictionary*)dict{
1.先創(chuàng)建一個類的對象
id objc =? [[self alloc]init];
2.//這里需要穿一個cout的地址绍弟,其中cout就是成員屬性總數(shù)
unsigned int count = 0;
3這個方法是把傳進(jìn)來的Model的成員變量屬性復(fù)制一分,其中Ivar*實(shí)際上就是只想一個成員變量的數(shù)組(注意區(qū)分成員屬性和屬性)
Ivar? *ivarPlist =class_copyIvarList(self, &count);
4.遍歷這個數(shù)字著洼,此時count的值已經(jīng)變成你成員變量屬性的個數(shù)
for (int i=0; i
(1):獲取到一個成員屬性名
Ivar ivar1 = ivarPlist[i];
(2):獲取到成員名
NSString *propertyName =? ? [NSString stringWithUTF8String: ivar_getName(ivar1)]
(3.)獲取到成員屬性(這個返回值是c語言樟遣,所以轉(zhuǎn)換了一下)
NSString *propertyType =? ? [NSString stringWithUTF8String:? ? ? ivar_getTypeEncoding(ivar1)];
(4),獲取key(注意成員屬性和屬性的區(qū)別)
NSString *key = [propertyName substringFromIndex:1];
(5)身笤,獲取Value
id Value= dict[key];
(6).通過KVC進(jìn)行賦值(因?yàn)閂alue如果為空豹悬,直接Crash,所以這里判斷了一下液荸,如果有值再去賦值)
if (Value) {
[objc setValue:Value forKey:key];//用kvc復(fù)制value不能為空
}
(7).return objc瞻佛;
}
這個方法也是比較容易理解的,上面只是介紹了一級字典轉(zhuǎn)模型,二級其實(shí)也非常簡單
二級字典轉(zhuǎn)模型:
假如我們返回?cái)?shù)據(jù)里面有一個字典伤柄,字典里面還有一個字典绊困,我們我們必須再創(chuàng)建一個UserMode類,然后自動生成屬性适刀,然后@class User; ? 再M(fèi)odel.h里面聲明這個屬性秤朗。
繼續(xù)在上面的for循環(huán)里面實(shí)現(xiàn)一下代碼:
判斷Value類型是不是字典,或者屬性名稱不包含NSDictionary
if ([Value isKindOfClass:[NSDictionary class]] &&![propertyType containsString:@"NS"]) {
1.直接將屬性類型轉(zhuǎn)換成類
Class modelClass =NSClassFromString(propertyType);
2.直接給賦值
if (modelClass) {
Value =? [modelClass modelWithDic:Value];
}
[注意:這里是不行的笔喉,因?yàn)榈陬愋娃D(zhuǎn)換成類返回值不是User? 而是@\"user “\]取视,所以你要進(jìn)行字符串截取,具體
propertyType substringFromIndex:range.location +range.length]
range =[propertyType rangeOfString:@"\""];
propertyType = [propertyType substringToIndex:range.location];
Class modelClass =NSClassFromString(propertyType);
}