在寫專案的時候,兩個動作,同樣的操作,但是傳遞不同的訊息,就想到了[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 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);
到此,這個警告算是完全消除了。
更加詳細請移步:
取消performSelector 方法
使用performselector 方法 self performselector selector didrunincurrmodel withobject nil afterdelay 3.0f 取消 nsobject cancelpreviousperformrequestswithtarge...
performSelector與直接呼叫的區別
performselector與直接呼叫的區別 1 直接呼叫 delegate image self didfinishwithimage image 2 使用 performselector呼叫 delegate performselector selector image didfinishwi...
延遲呼叫performSelector介紹
performselector void performselector sel aselector withobject id anargument afterdelay nstimeinterval delay 上述的方法可以靈活的運用,使用方便,只需要告訴他會呼叫什麼方法,然後在多長時間對他進...