博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
iOS: 消息通信中的Notification&KVO
阅读量:6550 次
发布时间:2019-06-24

本文共 3672 字,大约阅读时间需要 12 分钟。

在  中,我贴了张经典图:

 

其中的Model向Controller通信的Noification&KVO为何物呢?

在功能上说,delegate、Notification以及KVO的功能类似,都是作用于 OC中对象 的消息通信。但三者的使用场景是不同的。

简单的说Delegate是一种回掉函数,更多的用在一对一的场合,可参考  ;

Notification 用得较少,使用Notification Center,类似广播方式,所以更适合一对多的通信;

KVO,key-Value-Observing,观察者模式,适用于侦听另一对象的属性的变化。

三者的详细区别可以参考另一博文:http://mobile.51cto.com/iphone-386316.htm

Notification:

notification的使用十分简单,直接看代码:

 

//使用类方法获取实例    NSNotificationCenter *center = [NSNotificationCenter defaultCenter];    //增加2个消息监听,消息名都为logInfo,一个在本对象中监听,监听方法GetInfo;一个在oneobj对象监听,监听方法oneObjHandleInfo。    [center addObserver:self selector:@selector(GetInfo:) name:@"logInfo" object:nil];    [center addObserver:oneobj selector:@selector(oneObjHandleInfo:) name:@"logInfo" object:nil];    //发送消息,消息名logInfo,传递数据为一个NSString    [center postNotificationName:@"logInfo" object:@"00000"];

 

对应的2个接收方法:

//本对象中...-(void) GetInfo:(NSNotification *) notificaion{    //取得接受数据并打印    NSString *data = [notificaion object];    NSLog(@">> %@",data);}//OneObj对象中...-(void) oneObjHandleInfo:(NSNotification*) notification{    //取得接受数据并打印    NSString *data = [notification object];    NSLog(@">>OneOBJ %@",data);}

这样就实现了post一个消息的时候,对应的2个监听者都能收到消失并做出相关处理。最后要注意的是在不用的时候把对应的监听给remove掉。

[center removeObserver:self name:@"logInfo" object:nil];    [center removeObserver:oneobj name:@"logInfo" object:nil];

KVO:

在看KVO之前,有必要先了解下KVC,即,Key-Value Coding 键值对编程。通过key-value可以方便的存取数据。

具体的操作简单说就是:setValue:forKey:   valueForKey:

//book Object//.h#import 
@class Author;@interface Book : NSObject{ NSString *name; Author *author; float price; NSArray *relativeBooks;}@end//.m#import "Book.h"@implementation Book@end

 

Book *book = [[Book alloc] init];    [book setValue:@"iOS book" forKey:@"name"];    NSString *name = [book valueForKey:@"name"];    NSLog(@">> %@",name);        Author *author = [[Author alloc] init];    [author setValue:@"Zhan" forKey:@"name"];    [book setValue:author forKey:@"author"];        NSString *authorName = [book valueForKeyPath:@"author.name"];    NSLog(@">> %@",authorName);        [book setValue:@"100" forKey:@"price"];    NSLog(@">> %@",[book valueForKey:@"price"]);        Book *book1 = [[Book alloc] init];    [book1 setValue:@"4" forKey:@"price"];    Book *book2 = [[Book alloc] init];    [book2 setValue:@"6" forKey:@"price"];        NSArray *books = [NSArray arrayWithObjects:book1,book2,nil];    [book setValue:books forKey:@"relativeBooks"];    NSLog(@">>%@",[book valueForKeyPath:@"relativeBooks.price"]);

更详细的KVC介绍可以参考: http://marshal.easymorse.com/tech/objc-%E4%BD%BF%E7%94%A8kvc

KVO是基于kvc实现的,采取的是观察者的模式:

book4=[[Book alloc] init];    //增加观察者,为本类,keypath为book中的price对象,所以为price    [book4 addObserver:self forKeyPath:@"price" options:NSKeyValueObservingOptionOld|NSKeyValueObservingOptionNew context:nil];    //修改值    [book4 setValue:@"4" forKey:@"price"];
//回掉方法-(void) observeValueForKeyPath:(NSString *)keyPath                      ofObject:(id)object                        change:(NSDictionary *)change                       context:(void *)context{    NSLog(@"cel back");    if([keyPath isEqual:@"price"]){        NSLog(@">>>>>>>price is changed");        NSLog(@"old price is %@",[change objectForKey:@"old"]);        NSLog(@"new price is %@",[change objectForKey:@"new"]);    }}

这样便实现了当对象属性改变时,做出相应反应。

 更详细KVO实现也可以参照:http://blog.csdn.net/yuquan0821/article/details/6646400

那KVC、KVO内部是如何实现的呢?

    “一个对象在调用setValue的时候,(1)首先根据方法名找到运行方法的时候所需要的环境参数。(2)他会从自己isa指针结合环境参数,找到具体的方法实现的接口。(3)再直接查找得来的具体的方法实现。

    因为KVC的实现机制,可以很容易看到某个KVC操作的Key,而后也很容易的跟观察者注册表中的Key进行匹对。假如访问的Key是被观察的Key,那么我们在内部就可以很容易的到观察者注册表中去找到观察者对象,而后给他发送消息。”

详细check:http://www.cocoadev.cn/Cocoadev/KVO-20100222-0627.asp

 

iOS中oc通信的通知和KVO大概就是这些了。

 

 

 

你可能感兴趣的文章
henplus
查看>>
[转]iPhone/Mac Objective-C内存管理教程和原理剖析
查看>>
[转]感知器(Perceptron)原理和应用
查看>>
Jquery判断表里的某个值
查看>>
IE地址栏小图标问题
查看>>
使用lua写gui程序系列汇总
查看>>
.net 使用SqlBulkCopy极速插入数据到 SQL Server
查看>>
NHibernate二级缓存(第十一篇)
查看>>
ecshop完美解决前台和后台自动退出、购物车自动清空
查看>>
设计的四大原则
查看>>
使用Razor模板构建应用注意的细节
查看>>
给UIImageView增加点击事件
查看>>
【转】QRCode二维码的应用心得
查看>>
再议进程间通信 - 命名管道实现 (转)
查看>>
myeclipes启动tomcat6报错解决方案:a configuration error occ
查看>>
新手读懂五线谱
查看>>
什么是相关性以及为什么需要初始化它?
查看>>
c#如何禁止Form窗口调整大小,如何禁止combobox输入
查看>>
Java 编程下线程的生命周期
查看>>
『优秀作品』20个激发灵感的橙色风格网站设计
查看>>