KVC
用了这么久,是时候总结一下kvc
的原理了。
kvc
通过key直接访问对象的属性,或者给对象的属性直接赋值,因此在运行时动态的访问和修改对象的属性。
赋值方式:setValue:forKey:
譬如:[person setValue:@"wick" forKey:@"name"];
其底层逻辑为:
1、优先调用setName:属性值方法,找到setter方法完成赋值。
2、若找不到setName方法,kvc机制则检测+(BOOL)accessInstanceVariablesDirectly
方法有没有返回YES
,默认为YES
。若返回YES
,kvc
继续搜索有无名为name
的成员变量。若重写该方法,返回NO
,则此刻会调用-setValue: forUndefinedKey:
。
3、若未找到setName
方法,也未找到_name
成员变量,kvc则开始搜索_isName
的成员变量
4、如果以上方式都不命中,则kvc会执行-setValue: forUndefinedKey:
如果想禁用kvc,则+(BOOL)accessInstanceVariablesDirectly
返回NO即可
取值方式:valueForKey:
譬如:[person valueForKey:@"name"]
底层逻辑如下:
1、按照搜索顺序getName
,name
,isName
查找getter方法。
2、如果以上getter方法未命中,则会查找countOf:@"name"
,objectIn:@"name" atIndex:
或@"" atIndexes
方法。如果以上三个方法找到,则返回一个NSArray
的子类--NSKeyValueArray
3、如果以上方法未找到,会同时查找countOf:@"name"
,enumeratorOf:@"name"
,memberOf:@"name"
,如果查找到,则返回一个NSSet
所有的方法代理集合。
4、如果仍未找到,则检查+(BOOL)accessInstanceVariablesDirectly
返回YES
则按_name,_isName,name,isName
的顺序搜索变量名。如果返回NO
,则直接调-valueForUndefinedKey:
结束
网友评论