如何使用低级运行时API动态创建NSMutableArray?

时间:2011-07-09 05:43:53

标签: reflection nsmutablearray objective-c-runtime

简介

所以我一直在试验<objc/runtime.hApple's documentation中定义的Objective-C低级运行时API。你可以看到我玩in this gist的结果。

问题

我已经能够通过Objective-C动态创建一个简单的Hello World,只通过低级运行时API和C(参见上面的要点)。有用。现在我正在尝试使用相同的技术动态创建NSMutableArray。以下是代码片段:

Class nsmutablearray = objc_getClass("NSMutableArray");

id array = class_createInstance(nsmutablearray, 0);
id arrayAfterInit = objc_msgSend(array, sel_registerName("init"));

// get the count
objc_msgSend(arrayAfterInit, sel_registerName("count"))

但它给了我一个错误:

Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** -[NSArray count]: method only defined for abstract class. Define -[NSMutableArray count]!'

但如果我将上面代码段的中间部分更改为:

,它就能正常工作
id arrayAfterInit = objc_msgSend(nsmutablearray, sel_registerName("arrayWithCapacity:"), 10);

这有点令我困惑,因为它们应该是等同的。第一个代码段应该等同于调用[[NSMutableArray alloc] init]作为Objective-C语法,但在调用这些C函数时则不行。

任何关于此的灯都将非常感激。提前谢谢!

2 个答案:

答案 0 :(得分:0)

我不确定,但是我怀疑Apple在特定的子类中交换了一些运行时魔术,做了魔术。我打赌NSMutableArray虽然可见名称不是真正的实现。过去还有其他案例。

答案 1 :(得分:0)

我只是偶然发现了一个解决方法...工作......我已经更新了要点以证明它有效......

基本上,您不是调用class_createInstance,而是向alloc Class对象显式发送NSMutableArray消息。这有效:

id array = objc_msgSend(nsmutablearray, sel_registerName("alloc"));
id arrayAfterInit = objc_msgSend(array, sel_registerName("init"));

这让我们想知道:class_createInstance之后有什么意义(我正在为那个创建一个新的SO线程......)?