标签:
@selector 是什么?
1一种类型 SEL
2代表你要发送的消息(方法), 跟字符串有点像, 也可以互转.: NSSelectorFromString() / NSSelectorFromString()
3可以理解为类似函数指针的东西--是能让Objective-C动态调用方法的玩意.--是 object-c 的动态后绑定技术 可以通过字符串 访问的函数指针
4其实就是消息响应函数---选一个消息响应的函数地址给你的action
5@selector(function_name) 即取得一个function的id
SEL 类成员方法的指针
可以理解 @selector()就是取类方法的编号,他的行为基本可以等同C语言的中函数指针,只不过C语言中,可以把函数名直接赋给一个函数指针,而Object-C的类不能直接应用函数指针,这样只能做一个@selector语法来取.
它的结果是一个SEL类型。这个类型本质是类方法的编号(函数地址)
int test(int val)
{}
int (* c_func)(int val); //定义一个函数指针变量c_func = add ; //把函数addr地址直接赋给c_func
object-c的选择器,
@interface foo@end
SEL class_func ; //定义一个类方法指针class_func = @selector(add:int);
注意1、@selector是查找当前类(含子类)的方法。
举例:
父类.h文件
.h文件
ss.methodTest = @selector(parentMethod); 这句在运行期时,会寻找到父类中的方法进行调用。
ss.methodTest = @selector(SubMethod);//这句就在运行期时,会先寻找父类,如果父类没有,则寻找子类。
如果这里将ss.methodTest = @selector(test); 其中test即不是ss父类,也不是ss本身,也非SS子类,哪么这个时候在使用
[self performSelector:_methodTest withObject:nil];就会出现地址寻找出错 。
在处理用户-接口控件方面,AppKit充分发挥了在运行时改变接收者和消息的能力。
NSControl对象是一个图形设备,可以用来向应用程序发送指令,。大多实现了现实世界中的控制装置,例如button、switch、knob、text field、dial、menu item等。在软件中,这些设备处于用户和和应用程序之间。它们解释来自硬件设备,如键盘和鼠标的事件,并将它们翻译成应用程序特定的指令。例如,名为“Find”的按钮将会把鼠标点击事件翻译成开始搜索的应用程序指令。
AppKit为创建控件设备定义了模板,并定义了一些自己的现成设备。例如,NSButtonCell类定义了一个对象,可以指派给一个NSMatrix实例,并初始化它的大小、名称、图片、字体和键盘快捷键。当用户点击按钮(或使用键盘快捷键)时,NSButtonCell对象发送消息,指示应用程序工作。为此,NSButtonCell对象不仅要初始化图像、大小和名称,还要确定消息要发往何方和发给谁。相应地,NSButtonCell实例可以为一个action消息(它将在自己发送的消息中使用的对象选择器)和一个target(接收该消息的对象)进行初始化。
如果Objective-C不允许改变消息,所有的NSButtonCell对象将不得不发送相同的消息,方法的名字将在NSButtonCell源代码中写死。与简单的实现将用户action转换为action消息的机制不同,按钮单元和其他控件不得不限制消息的内容。受限的消息会使很多对象难以响应多于一个的按钮单元。要么每个按钮有一个target,要么target对象能发现消息来自于那个按钮,并做相应处理。每次在重新布局用户接口时,你也必须实现响应action消息的方法。动态消息的缺乏将会带来不必要的麻烦,但Objective-C很好地避免了这一点。
从前面的例子可以得知如果SEL不是自身的方法,在调用时就会出错,引起CRASH,哪么如何避免消息传递引起的错误。见下文章:
如果一个对象接收了一条消息去执行不归它管的方法,就会产生错误结果。这和调用一个不存在的函数是同一类错误。但是,因为消息发生在运行时,错误只有在程序执行后才会出现。
当消息选择器是常数并且接收对象类已知时,处理这种错误相对容易。在写程序时,你可以确保接收者能够响应。如果接收者时静态类型,编译器将替你完成该测试。
但是,如果消息选择器或接收者是变化的,那么只能在运行时进行相关测试。NSObject类中定义的respondsToSelector:方法可以测试一个接收者是否能够响应某条消息。它将方法选择器作为参数并返回接收者是否已经访问了与选择器相匹配的一个方法:
注意:一个对象在收到不是自己负责直接响应的消息时可以转发该消息给其他对象。这种情况下,从调用者的角度来看,对象直接处理了消息,尽管该对象是通过转发消息给其他对象来处理的。
注意2、查找类方法时,除了方法名,方法参数也查询条件之一.
这个主要是多个参数时需要注意,如:
注意3、可以用字符串来找方法 SEL 变量名 = NSSelectorFromString(方法名字的字符串);
注意4、 可以运行中用SEL变量反向查出方法名字字符串,如:NSString *method = NSStringFromSelector(setWidthHeight);
注意5、SEL 查找的方法不支持类方法(即静态方法,在C++中带static关键字的,在OBJECT-C中即方法前带+号的,DELPHI中为class function)。
SEL就是对方法的一种包装。包装的SEL类型数据它对应相应的方法地址,找到方法地址就可以调用方法。在内存中每个类的方法都存储在类对象中,每个方法都有一个与之对应的SEL类型的数据,根据一个SEL数据就可以找到对应的方法地址,进而调用方法。
SEL就是对方法的一种包装。包装的SEL类型数据它对应相应的方法地址,找到方法地址就可以调用方法
1.方法的存储位置
2.SEL对象的创建
3.SEL对象的其他用法
标签:
原文地址:http://www.cnblogs.com/kenshinobiy/p/4866082.html