賦值過程:
- 先找相關(guān)方法:set<key>:,_set<key>:,setIs<key>:
- 若沒有相關(guān)方法則:+ (BOOL)accessInstanceVariablesDirectly判斷是否可以直接訪問成員變量
- 如果accessInstanceVariablesDirectly返回YES,繼續(xù)找相關(guān)成員變量_<key>,_is<key>,<key>,is<key>,如果沒找到則拋出異常setValue: forUndefinedKey:
- 如果accessInstanceVariablesDirectly返回NO,直接執(zhí)行KVC的setValue: forUndefinedKey:
取值過程:
1 .先找相關(guān)方法:get<key>:,<key>:
2 .若沒有相關(guān)方法則:+ (BOOL)accessInstanceVariablesDirectly判斷是否可以直接訪問成員變量
3 .如果accessInstanceVariablesDirectly返回YES,繼續(xù)找相關(guān)成員變量_<key>,_is<key>,<key>,is<key>,如果沒找到則拋出異常valueForUndefinedKey:
4 .如果accessInstanceVariablesDirectly返回NO,直接執(zhí)行KVC的valueForUndefinedKey:
賦值的時候要注意:
1:非對象類型的屬性,賦值的時候,值不可以為空,否則會爆報:setNilValueForKey錯誤,為了解決賦值為空的報錯,需要寫下setNilValueForKey方法,不至于崩潰
@implementation Person
//非對象類型,值不能為空
- (void)setNilValueForKey:(NSString *)key{
NSLog(@"setNilValueForKey :%@",key);
}
@end
2:對不存在的屬性賦值會報錯:setValue:forUndefinedKey:
-(void)setValue:(id)value forUndefinedKey:(NSString *)key
{
NSLog(@"%@不存在",key);
}
賦值前驗證值的合法性:
- (BOOL)validateValue:(inout id _Nullable __autoreleasing *)ioValue error:(out NSError * _Nullable __autoreleasing *)outError{
validate<value>工作原理:
- 先找一下你的類中是否實現(xiàn)了方法validate<Value>:error:
- 如果實現(xiàn)了就會根據(jù)實現(xiàn)方法里面的自定義邏輯返回NO或者YES,如果沒有實現(xiàn)這個犯法,則系統(tǒng)默認(rèn)返回YES
比如我們設(shè)置人的年齡不能超過200歲,可以有如下判斷:
- (BOOL)validateAge:(inout id _Nullable __autoreleasing *)ioValue error:(out NSError * _Nullable __autoreleasing *)outError{
NSNumber *value = (NSNumber*)*ioValue;
int age = [value intValue];
if (age <= 0 || age >= 200) {
return NO;
}
return YES;
}