iOS 面試題(三)什么時候在 block 中不需要使用 weakSelf

我們知道,在使用 block 的時候,為了避免產(chǎn)生循環(huán)引用,通常需要使用 weakSelf 與 strongSelf,寫下面這樣的代碼:

__weak typeof(self) weakSelf = self;
[self doSomeBackgroundJob:^{
? ?__strong typeof(weakSelf) strongSelf = weakSelf;
? ?if (strongSelf) {
? ? ? ?...
? ?}
}];

那么請問:為什么 block 里面還需要寫一個 strong self,如果不寫會怎么樣?

在 block 中先寫一個 strong self,其實是為了避免在 block 的執(zhí)行過程中,突然出現(xiàn) self 被釋放的尷尬情況。通常情況下,如果不這么做的話,還是很容易出現(xiàn)一些奇怪的邏輯,甚至閃退。

我們以AFNetworking中的AFNetworkReachabilityManager.m的一段代碼舉例:

__weak __typeof(self)weakSelf = self;
AFNetworkReachabilityStatusBlock callback = ^(AFNetworkReachabilityStatus status) {
? ?__strong __typeof(weakSelf)strongSelf = weakSelf;
? ?strongSelf.networkReachabilityStatus = status;
? ?if (strongSelf.networkReachabilityStatusBlock) {strongSelf.networkReachabilityStatusBlock(status);
? ?}
};

如果沒有strongSelf的那行代碼,那么后面的每一行代碼執(zhí)行時,self都可能被釋放掉了,這樣很可能造成邏輯異常。

特別是當(dāng)我們正在執(zhí)行 strongSelf.networkReachabilityStatusBlock(status); 這個 block閉包時,如果這個 block 執(zhí)行到一半時 self 釋放,那么多半情況下會 Crash。

這里有一篇文章詳細(xì)解釋了這個問題:
昨天的讀者中,拓荒者 和 陳祥龍 同學(xué)在評論中也正確回答出了本題。

拓荒者:
1.在block里使用strongSelf是防止在block執(zhí)行過程中self被釋放。 2.可以通過在執(zhí)行完block代碼后手動把block置為nil來打破引用循環(huán),AFNetworking就是這樣處理的,避免使用者不了解引用循環(huán)造成內(nèi)存泄露。實際業(yè)務(wù)中暫時沒遇到這種需求,請巧哥指點什么情況下會有這種需求。

陳祥龍:
strongSelf 一般是在為了避免 block 回調(diào)時 weak Self變成了nil ,異步執(zhí)行一些操作時可能會出現(xiàn)這種情況,不知道我說得對不對。因業(yè)務(wù)需要不能使用weakSelf 這種情況還真沒遇到過

另外,還有讀者提了兩個有意思的問題,大家可以思考一下:
Yuen 提問:“數(shù)組” 和 “字典” 的 enumeratXXXUsingBlock: 是否要使用 weakSelf 和 strongSelf 呢?
瀟湘雨同學(xué)提問:block 里 strong self 后,block 不是也會持有 self 嗎?而 self 又持有 block ,那不是又循環(huán)引用了?
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容