我知道如何使用 @selector(MyMethodName:)在编译时创建 SEL ,但我想要做的是从动态创建一个选择器的NSString 。这甚至可能吗?

我能做什么:

SEL selector = @selector(doWork:);
[myobj respondsToSelector:selector];

我想做什么:(伪代码,这显然不起作用)

SEL selector = selectorFromString(@"doWork");
[myobj respondsToSelector:selector];

我一直在搜索Apple API文档,但是没有找到一种不依赖于编译时 @selector(myTarget :) 语法的方法。

有帮助吗?

解决方案

我不是Objective-C程序员,只是一个同情者,但也许 NSSelectorFromString 就是您所需要的。它提到了你可以使用的运行时参考中的明确表述它将字符串转换为选择器。

其他提示

根据XCode文档,你的伪代码基本上是正确的。

  

使用@selector()指令在编译时为SEL变量赋值是最有效的。但是,在某些情况下,程序可能需要在运行时将字符串转换为选择器。这可以使用NSSelectorFromString函数完成:

setWidthHeight = NSSelectorFromString(aBuffer);

编辑:糟糕,太慢了。 :P

我不得不说它比以前的受访者的答案可能暗示的更复杂 ...如果你确实想要创建一个选择器。 ..而不仅仅是“召唤一个”你“已经四处走动”...

您需要创建一个将由“new”调用的函数指针。方法..所以对于像 [self theMethod:(id)methodArg]; 这样的方法,你要写...

void (^impBlock)(id,id) = ^(id _self, id methodArg) { 
     [_self doSomethingWith:methodArg]; 
};

然后你需要动态生成 IMP 块,这次,传递,“self”, SEL ,以及任何参数......

void(*impFunct)(id, SEL, id) = (void*) imp_implementationWithBlock(impBlock);

并将其添加到您的班级,以及整个吸盘的准确方法签名(在本例中为" v @:@" ,void return,object caller,object argument)

 class_addMethod(self.class, @selector(theMethod:), (IMP)impFunct, "v@:@");

你可以在我的一个回购中看到这种 运行时shenanigans 的一些很好的例子。

我知道很久以前就已经回答了这个问题,但我仍想分享。这也可以使用 sel_registerName 来完成。

问题中的示例代码可以像这样重写:

SEL selector = sel_registerName("doWork:");
[myobj respondsToSelector:selector];
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top