NSNotification
1.什么是NSNotification
每个运行中的application都有一个NSNotificationCenter的成员变量,它的功能就类似与公共栏,对象在这里注册关注每个确定Notification,我们把这些注册对象叫做observer,其他的一些对象会给center发送Notification,center将该notification转发
所有注册对该notification感兴趣的对象,我们把这些发送Notification的对象叫做poster。
很多的标准cocoa类会发送Notification,在改变Size的时候,windows会发送Notification;选择tableview中的一行时,tableview会发送Notification;我们可以在帮助文档中查看标准cocoa对象发送的Notification。
[Notification就是设计模式中的观察者模式, cocoa为我们实现了该模式, 就像Java也有同样的实现一样]。
2.创建一个通知对象:使用notificationWithName:object: 或者 notificationWithName:object:userInfo:
NSNotification* notification = [NSNotification notificationWithName:kImageNotificationLoadFailed(connection.imageURL)
object:self
userInfo:[NSDictionary dictionaryWithObjectsAndKeys:error,@"error",connection.imageURL,@"imageURL",nil]];
这里需要注意的是,创建自己的通知并不是必须的。而是在创建自己的通知之前,采用NSNotificationCenter类的方法 postNotificationName:object: 和 postNotificationName:object:userInfo:更加便利的发出通知。这种情况,一般使用NSNotificationCenter的类方法defaultCenter就获得默认的通知对象,这样你就可以给该程序的默认通知中心发送通知了。注意:每一个程序都有一个自己的通知中心,即NSNotificationCenter对象。该对象采用单例设计模式,采用defaultCenter方法就可以获得唯一的NSNotificationCenter对象。
注意:NSNotification对象是不可变的,因为一旦创建,对象是不能更改的。
3.注册通知:addObserver:selector:name:object:
可以看到除了添加观察者之外,还有其接收到通知之后的执行方法入口,即selector的实参。因此为了进行防御式编程,最好先检查观察者是否定义了该方法。例如:添加观察者代码有
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(aWindowBecameMain:)
name:NSWindowDidBecomeMainNotification object:nil];
这里保证了self定义了aWindowBecameMain:方法。而对于一个任意的观察者observer,不能保证其对应的selector有aWindowBecameMain:,可采用[observer respondsToSelector:@selector(aWindowBecameMain:)]] 进行检查。所以完整的添加观察者过程为:
if([observer respondsToSelector:@selector(aWindowBecameMain:)]) {
[[NSNotificationCenter defaultCenter] addObserver:observer selector:@selector(aWindowBecameMain:) name:NSWindowDidBecomeMainNotification object:nil];
}
注意到addObserver:selector:name:object:不仅指定一个观察者,指定通知中心发送给观察者的消息,还有接收通知的名字,以及指定的对象。一般来说不需要指定name和object,但如果仅仅指定了一个object,观察者将收到该对象的所有通知。例如将上面的代码中name改为nil,那么观察者将接收到object对象的所有消息,但是确定不了接收这些消息的顺序。如果指指定一个通知名称,观察者将收到它每次发出的通知。例如,上面的代码中object为nil,那么客户对象(self)将收到任何对象发出NSWindowDidBecomeMainNotification通知。如果既没有指定指定object,也没有指定name,那么该观察者将收到所有对象的所有消息。
4.发送通知:postNotificationName:object:或者performSelectorOnMainThread:withObject:waitUntilDone:
例如程序可以实现将一个文本可以进行一系列的转换,例如对于一个实例、RTF格式转换成ASCII格式。而转换在一个类(如Converter类)的对象中得到处理,在诚寻执行过程中可以加入或者删除这种转换。而且当添加或者删除Converter操作时,你的程序可能需要通知其他的对象,但是这些Converter对象并不需要知道被通知对象是什么,能干什么。你只需要声明两个通知,"ConverterAdded" 和 "ConverterRemoved",并且在某一事件发生时就发出这两个通知。
当一个用户安装或者删除一个Converter,它将发送下面的消息给通知中心:
[[NSNotificationCenter defaultCenter]
postNotificationName:@"ConverterAdded" object:self];
或者是
[[NSNotificationCenter defaultCenter]
postNotificationName:@"ConverterRemoved" object:self];
通知中心将会区分它们对象对这些通知感兴趣并且通知他们。如果除了关心观察者的通知名称和观察的对象,还关心其他之外的对象,那么就把之外的对象放在通知的可选字典中,或者用方法postNotificationName:object:userInfo:。
而采用performSelectorOnMainThread:withObject:waitUntilDone:则是直接调用NSNotification的方法postNotification,而postNotificationName和object参数可以放到withObject的实参中。例如:
[[NSNotificationCenter defaultCenter] performSelectorOnMainThread:@selector(postNotification:) withObject:notification waitUntilDone:YES];//注意这里的notification为自定义的一个通知对象,可定义为NSNotification* notification = [NSNotification notificationWithName:@"ConverterAdded"object:self];//那么它的作用与上面的一致
5.移除通知:removeObserver:和removeObserver:name:object:
其中,removeObserver:是删除通知中心保存的调度表一个观察者的所有入口,而removeObserver:name:object:是删除匹配了通知中心保存的调度表中观察者的一个入口。
这个比较简单,直接调用该方法就行。例如:
[[NSNotificationCenter defaultCenter] removeObserver:observer name:nil object:self];
注意参数notificationObserver为要删除的观察者,一定不能置为nil。
NSNotification的更多相关文章
- iOS---正确使用NSNotification对象
我们在开发程序的时候,程序内不同对象间的通信是不可避免的,iOS中主要有以下这些通信方式: iOS中的通信方式 图中按照耦合度的强弱和通信的形式(一对一还是一对多)进行了划分,这篇文章我们主要说一下N ...
- 04 KVC|KVO|Delegate|NSNotification区别
一. iOS 中KVC.KVO.NSNotification.delegate 在实际的编程中运用的非常多,掌握好他们的运行原理和使用场合对于我们程序的开发将会带来事办工倍的效果: 二. KVC ...
- NSNotification --关于通知
一. 通知(NSNotification)的发送(Post)和注册(add)都必须借助于通知中心(NSNotificationCenter) 发送通知: NSNotificationCenter *c ...
- (ios) nsnotification总结
1 文本输入,键盘显示时,view向上,键盘隐藏时,view向下 1.1 注册键盘显示,关闭通知,并实现主界面上下变动 [[NSNotificationCenter defaultCenter] a ...
- KVC、KVO、NSNotification、delegate 总结及区别
1.KVC,即是指 NSKeyValueCoding,一个非正式的Protocol,提供一种机制来间接访问对象的属性.而不是通过调用Setter.Getter方法访问.KVO 就是基于 KVC 实现的 ...
- ios基础篇(十八)——Delegate 、NSNotification 和 KVO用法及其区别
一.Delegate Delegate本质是一种程序设计模型,iOS中使用Delegate主要用于两个页面之间的数据传递.iphone中常用@protocol和delegate的机制来实现接口的功能. ...
- iOS NSNotification的使用
如果在一个类中想要执行另一个类中的方法可以使用通知 1.创建一个通知对象:使用notificationWithName:object: 或者 notificationWithName:object:u ...
- ios delegate, block, NSNotification用法
ios中实现callback可以通过两种方法,委托和NSNotification 委托的话是一对一的关系,例如一个UIViewController里有一个tableView, 将该viewContro ...
- NSNotification Name 最佳写法
本文主要借探讨NSNotificationName的最佳写法的机会,学习下extern, static, const, #define 和常量指针与指针常量等的特性和用法. 1.NSNotificat ...
- NSNotification系统通知优化
最近在github上看到了LRNotificationObserver这个项目,看了一下实现方式,作者通过ARC机制实例化注册对象子类与关联对象的方法来管理注册对象的生命周期.从而省去了系统通知移除的 ...
随机推荐
- 表达式求值--Java实现
/*将中缀表达式--转化为后缀表达式--属于栈的一种应用 *具体思路: *1.扫描字符串,遇到操作数字符直接不管,存到一个字符串里边 *2.操作符优先级比较--定义了方法 * 栈中优先级高:出栈存进字 ...
- 实验测试之------创建DBlink,查询远端的yang用户下的abcdedfa表,创建同义词
--测试环境,20远端,30本地: --准备1,20远端建立表的同义词,用户信息: 1.11 ---------------------------------------------------准备 ...
- Judge Route Circle --判断圆路线
Initially, there is a Robot at position (0, 0). Given a sequence of its moves, judge if this robot m ...
- H5新特性汇总
H5新特性: 新增选择器 document.querySelector.document.querySelectorAll 拖拽释放(Drag and drop) API 媒体播放的 video 和 ...
- 【ThinkPHP框架学习 】(1) --- thinkphp 3.2.3 验证码验证使用教程分享
框架版本:ThinkPHP框架 thinkphp 3.2.3 生成验证码 下面是最简单的方式生成验证码: $Verify = new \Think\Verify(); $Verify-> ...
- 平衡二叉树(AVL树)
参考资料 http://www.cnblogs.com/Cmpl/archive/2011/06/05/2073217.html http://www.cnblogs.com/yc_sunniwell ...
- Longest Common Substring(最长公共子序列)
Longest Common Substring Time Limit: 8000/4000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Ot ...
- Lombok 使用小结
Lombok 简介 Lombok 是一种 Java 实用工具,可用来帮助开发人员消除 Java 的冗长,尤其是对于简单的 Java 对象(POJO).它通过注释实现这一目的.通过在开发环境中实现 Lo ...
- 多线程环境下非安全Dictionary引起的“已添加了具有相同键的项”问题
问题: 代码是在多线程环境下,做了简单的Key是否存的判断, 测试代码如下: public class Program { static Dictionary<string, Logger> ...
- MSSQL 备份数据库还原
-- 完整还原RESTORE DATABASE XXXX FROM DISK = 'd:\XXXX.bak' WITH MOVE 'XXXX' TO 'D:\MSSQL\Data\XXXX.mdf', ...