在 Xcode 中,如果我写 -
id a;
当我开始向 a, [a ... 写消息时,Xcode 给出了一长串自动完成建议。这些建议是在什么基础上提出的(显然是所有可能的方法名称)?
我可以编译任何方法调用,比如
[a viewDidLoad];
我知道 id 可以接收任何消息。但
[a asdfgh]; //asdfgh random string
不编译。
在 Xcode 中,如果我写 -
id a;
当我开始向 a, [a ... 写消息时,Xcode 给出了一长串自动完成建议。这些建议是在什么基础上提出的(显然是所有可能的方法名称)?
我可以编译任何方法调用,比如
[a viewDidLoad];
我知道 id 可以接收任何消息。但
[a asdfgh]; //asdfgh random string
不编译。
这些建议是在什么基础上提出的(显然是所有可能的方法名称)?
这些建议有点聪明:据我所知,它们计入类和对象的采用协议。由于id
是通用的,因此,任何现有的消息都可能被发送给它(它可能会或可能不会响应),Xcode 建议它在任何类或协议中找到的任何内容。
但是[a asdfgh];不编译
因为编译器确实提供了某种程度的保护。如果一个选择器根本没有在任何地方声明,它假定选择器不存在,因此不可能将它发送到任何对象,因此它会抱怨。
在这里你可以看到是什么id
typedef struct objc_object {
Class isa;
} *id;
它根本不是void *
,而是指向struct
包含单个成员的指针,指向类定义。因此,它可以在运行时采用任何数据类型的形式。动态类型。
在编译时它检查正确的方法名称,如果它存在?
[a asdfgh];
产生错误,因为没有带有 name 的方法/选择器asdfgh
。
虽然[a viewDidLoad];
编译得很好,但是在运行时它可能会崩溃!