performSelector引起的警告解决办法

             在写项目的时候,两个动作,同样的操作,但是传递不同的消息,就想到了[target performSelector:sell withObject:nil],写完后发现很正常,但是有个警告,本能的就觉得不舒服,仔细一看:performSelector may cause a leak because itsselector is unknown。

           既然编译报警告,我们就不能不管。引起这个警告的原因是什么呢?

   我们在调用这些方法的时候有可能返回的是void 或者其他 non-Objects,我们可以忽略这个警告,但是不建议这么做。我们知道oc的内存管理机制,有retain必然有release。在arc模式下,这些都由编译器帮我们做了。但是,假如我们的方法返回的是non-Objects(当然,包括void),这时retain或者release,我们的程序就有可能crash掉。

既然知道了原因,那么解决办法呢?

我们有两种解决办法

第一种:

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Warc-performSelector-leaks"
    [target performSelector: sel withObject: nil];
#pragma clang diagnostic pop
也可以定义一个宏

#define SuppressPerformSelectorLeakWarning(Stuff) \
do { \
_Pragma("clang diagnostic push") \
_Pragma("clang diagnostic ignored \"-Warc-performSelector-leaks\"") \
Stuff; \
_Pragma("clang diagnostic pop") \
} while (0)
SuppressPerformSelectorLeakWarning(
    [target performSelector:sel withObject:nil]
);

 这样使用起来更方便,但是这种方法并没有真正消除这个警告 
  

第二种解决办法:

SEL selector = NSSelectorFromString(@"someMethod");
IMP imp = [_controller methodForSelector:selector];
void (*func)(id, SEL) = (void *)imp;
func(_controller, selector);
还有另一种写法,不过读起来费力

SEL selector = NSSelectorFromString(@"someMethod");
((void (*)(id, SEL))[target methodForSelector:selector])(target, selector);

到此,这个警告算是完全消除了。

更加详细请移步:http://stackoverflow.com/questions/7017281/performselector-may-cause-a-leak-because-its-selector-is-unknown




你可能感兴趣的:(iOS开发)