iOS--Day05---KVC,KVO

来源:http://www.cnblogs.com/jay-dong/archive/2012/12/13/2815778.html

熟悉oc语法的同学也许都会懂得这么一点:在oc中,类的成员变量或是方法是没有绝对私有的。

私有方法直接通过类实例无法访问,但可以借助oc的“编译运行时”机制,也即“瞎子摸黑”机制(个人理解:只要确定了该类有方法A,管你是私有共有,我用performSelector函数就能调用你),说到这,也许有同学会自然想起,那私有变量如何去访问呢?貌似以前还真没这样搞过,然而现实是可以的,只不过一般我们把变量设为类的私有变量后是不希望自己或是其他人再去访问的,不然我只能说你自己又在找贱了。。。。。。。。。。。。。。

好吧,言归正传,这篇文章主要是想介绍下oc中的KVC、KVO、KVB的实现机制,当然跟我上面说的那些肯定是有关系的啦。。

1. KVC:  key-value coding(键值编码)

它 是一种使用字符串标识符,间接访问对象属性的机制,它是很多技术的基础。主要的方法就两对方法:(setValue:forKey,valueForKey)、setValue:forKeyPath,valueForKeyPath);这个东西有什么作用呢,我先不说原理,先说怎么用,例子如下:

@interface A { NSString* foo; } ... // 其它代码 @end @interface B { NSString* bar; A* myA; } ... // 其它代码 @end @implementation B ... // 假设 A 类型的对象 a,B 类型的对象 b A* a = ...; B* b = ...; NSString* s1 = [a valueForKey:@"foo"]; // 正确 NSString* s2 = [b valueForKey:@"bar"]; // 正确 NSString* s3 = [b valueForKey:@"myA"]; // 正确 NSString* s4 = [b valueForKeyPath:@"myA.foo"]; // 正确 NSString* s5 = [b valueForKey:@"myA.foo"]; // 错误 NSString* s6 = [b valueForKeyPath:@"bar"]; // 正确 ... @end

其实上面说的那两对方法使用上基本是一样的,只是valueForKeyPath的值是一个路径(路径之间以点号 . 分割),比如数据成员就是对象自己,寻值过程就会向下深入下去。
注意,这里的数据成员的名字都是使用的字符串的形式。这种使用方法的最好的用处在于将数据(名字)绑定到一些触发器(尤其是方法调用)上,
例如键值对观察(Key-Value Observing, KVO)等。

上述代码说明了类的成员变量也可以使用基类NSObject的那两对方法去访问,不一定直接通过类实例访问,但是这种方式还是有一定的风险,具体危险情况请参考这个:http://www.devbean.info/2011/04/from_cpp_to_objc_20/
然后我再说下原理,是俺Copy过来的,大家观赏下:
KVC运用了一个isa- swizzling技术。isa-swizzling就是类型混合指针机制。KVC主要通过isa- swizzling,来实现其内部查找定位的。
isa指针,如其名称所指,(就是is a kind of的意思),指向维护分发表的对象的类。该分发表实际上包含了指向实现类中的方法的指针,和其它数据。

比如说如下的一行KVC的代码:

[site setValue:@"sitename" forKey:@"name"];
就会被编译器处理成:

SEL sel = sel_get_uid ("setValue:forKey:");
IMP method = objc_msg_lookup (site->isa,sel);
method(site, sel, @"sitename", @"name");
首先介绍两个基本概念:

(1)SEL数据类型:它是编译器运行Objective-C里的方法的环境参数。

(2)IMP数据 类型:他其实就是一个编译器内部实现时候的函数指针。当Objective-C编译器去处理实现一个方法的时候,就会指向一个IMP对象,这个对象是C语言表述的类型(事实上,在Objective-C的编译器处理的时候,基本上都是C语言的)。
这下KVC内部的实现就很清楚的清楚了:一个对象在调用setValue的时候,
(1)首先根据方法名找到运行方法的时候所需要的环境参 数。
(2)他会从自己isa指针结合环境参数,找到具体的方法实现的接口。
(3)再直接查找得来的具体的方法实现。

2.KVO:  key-value observing(键值监听)与KVB: key-value Binding(键值绑定)

这两个机制是结合起来使用的,分别说下,

Key-Value Observing (简写为KVO):当指定的对象的属性被修改了,允许对象接受到通知的机制。每次指定的被观察对象的属性被修改的时候,KVO都会自动的去通知相应的观察者。

KVO的优点

当 有属性改变,KVO会提供自动的消息通知。这样的架构有很多好处。首先,开发人员不需要自己去实现这样的方案:每次属性改变了就发送消息通知。这是KVO机制提供的最大的优点。因为这个方案已经被明确定义,获得框架级支持,可以方便地采用。开发人员不需要添加任何代码,不需要设计自己的观察者模型,直接可以在工程里使用。其次,KVO的架构非常的强大,可以很容易的支持多个观察者观察同一个属性,以及相关的值。

KVB实现的两个基本方法
1:为对象添加观察者OBserver  addObserver:forKeyPath:options:context:
2:观察者OBserver收到信息的处理函数   observeValueForKeyPath:ofObject:change:context:

KVO和KVB最明显的使用场景就是在一些界面实时显示行很强的地方,比如股票走向、售票余额等,这种方式免去了我们自己操作通知的麻烦,想到这,我发现当初点金和91市场中下载页面进度的显示也完全可以采用这种方式。

先说到这儿吧,更精彩的待续。。。。。。。。

原英文链接:http://maniacdev.com/2012/12/helper-classes-for-easy-cocoa-touch-key-value-observing-kvo-and-key-value-binding-kvb/

1、setValue:forKey: 可以访问到setXXX:方法。

2、valueForKey:可以访问到实例变量和不带参数的方法。

3、performSelector可以访问所有方法。

时间: 2024-10-04 10:11:50

iOS--Day05---KVC,KVO的相关文章

iOS 的 KVC & KVO的底层实现原理

KVO 内部实现原理 1. KVO 是基于runtime机制实现的. 2. 当某个类的对象第一次被观察时,系统就会在运行期动态的创建该类的一个派生类,在这个派生类中重写基类中任何被观察属性的setter方法; 派生类在被重写的setter方法中实现真正的通知机制 (Person -> NSKVONotifying_Person) 1.KVC,即是指 NSKeyValueCoding,一个非正式的Protocol,提供一种机制来间接访问对象的属性.而不是通过调用Setter.Getter方法访问.

iOS开发 kvc kvo 委托代理 协议 通知 简述 和使用场景

kvc: 简单来说, 是存取类属性, 通过字符串来访问对象属性. 1.只针对类属性,设置键值对 2.设置setValue: forKey:,即forKey只能为类属性 3.取值valueForKey kvo: 通过kvc 的方式修改被观察者的属性时,主动通知观察者. 1.利用KVC对类属性进行设置 2.注册observing对象addObserver:forKeyPath:options:context: 3.观察者类必须重写方法 observeValueForKeyPath:ofObject:

iOS 中KVC、KVO、NSNotification、delegate 总结及区别

iOS 中KVC.KVO.NSNotification.delegate 总结及区别 1.KVC,即是指 NSKeyValueCoding,一个非正式的Protocol,提供一种机制来间接访问对象的属性.而不是通过调用Setter.Getter方法访问.KVO 就是基于 KVC 实现的关键技术之一. Demo: @interface myPerson : NSObject { NSString*_name; int      _age; int      _height; int      _w

【iOS】KVC 与 KVO

一.KVC与KVO *"KVC":key value Coding(键值编码) *目的:间接的修改或获取对象的属性,降低程序(类与类)之间的耦合度. *"KVO":key value Observer(键值观察),观察者模式.(检测模型变化用的多) *目的:通常用于观察某个对象的某个属性发生变化时,及时做出相应. 二.KVC的使用方式 KVC被称为iOS开发平台的大招!!! 能快速修改对象属性. *[p1setValue:@"xxxx"forKe

iOS KVC/KVO总结

http://www.cnblogs.com/QM80/p/3647819.html 如果要修改对象的属性值 1.一般情况下是直接利用对象属性的set方法来修改: Student *stu = [[Student alloc] init]; // set方法的两种书写格式 [stu setAge:10]; stu.age = 10; 2.但是如果不知道对象类型呢?那么就可以运用KVC键值编码(Key Value Coding) 间接的修改对象属性 KVC实现方式是:使用字符串来描述对象需要修改的

04 KVC|KVO|Delegate|NSNotification区别

一. iOS 中KVC.KVO.NSNotification.delegate 在实际的编程中运用的非常多,掌握好他们的运行原理和使用场合对于我们程序的开发将会带来事办工倍的效果:   二. KVC  key-Value coding,键值编码,级通过制定的key我们能查找到对应的value,也能给对应的key附上value值.这一点类似于我们的字典查找.比如我们需要查找哪一页的内容,只需要将字典的唯一的页码(也就是key)找到,就能够知道这一页的内容,根据这个字典这一特性,程序猿们发明了Dic

转:KVC/KVO原理详解及编程指南

作者:wangzz 原文地址:http://blog.csdn.net/wzzvictory/article/details/9674431 转载请注明出处 如果觉得文章对你有所帮助,请通过留言或关注微信公众帐号wangzzstrive来支持我,谢谢! 前言: 1.本文基本不讲KVC/KVO的用法,只结合网上的资料说说对这种技术的理解. 2.由于KVO内容较少,而且是以KVC为基础实现的,本文将着重介绍KVC部分. 一.简介 KVC/KVO是观察者模式的一种实现,在Cocoa中是以被万物之源NS

KVC/KVO原理详解及编程指南(转载)

KVC/KVO原理详解及编程指南 作者:wangzz 原文地址:http://blog.csdn.net/wzzvictory/article/details/9674431 转载请注明出处 如果觉得文章对你有所帮助,请通过留言或关注微信公众帐号wangzzstrive来支持我,谢谢! 前言: 1.本文基本不讲KVC/KVO的用法,只结合网上的资料说说对这种技术的理解. 2.由于KVO内容较少,而且是以KVC为基础实现的,本文将着重介绍KVC部分. 一.简介 KVC/KVO是观察者模式的一种实现

KVC/KVO原理详解及编程指南

http://blog.csdn.net/wzzvictory/article/details/9674431 2.KVC/KVO实现原理 键值编码和键值观察是根据isa-swizzling技术来实现的,主要依据runtime的强大动态能力.下面的这段话是引自网上的一篇文章: http://blog.csdn.net/kesalin/article/details/8194240 当某个类的对象第一次被观察时,系统就会在运行期动态地创建该类的一个派生类,在这个派生类中重写基类中任何被观察属性的

深入理解 KVC\KVO 实现机制 — KVC

深入理解 KVC\KVO 实现机制  —  KVC  KVC和KVO都属于键值编程而且底层实现机制都是isa-swizzing,所以本来想放在一起讲的.但是篇幅有限所以就分成了两篇博文KVO实现机制传送门 KVC概述 KVC是Key Value Coding的简称.它是一种可以通过字符串的名字(key)来访问类属性的机制.而不是通过调用Setter.Getter方法访问. 关键方法定义在 NSKeyValueCodingProtocol KVC支持类对象和内建基本数据类型. KVC使用 获取值v