You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

嵌套dispatch_after块中strongSelf/weakSelf的用法正确性问询

代码中strongSelf/weakSelf的使用规范与优化建议

一、当前代码的问题分析

  • 内层嵌套的strongSelf2属于冗余声明:外层block已经通过strongSelf持有了self,后续嵌套的block会自动捕获这个strongSelf,只要strongSelf有效,self就不会被释放,重复声明没有必要。
  • 硬编码延迟存在风险:两次dispatch_after的0.1秒延迟是固定值,依赖UI渲染的时机,在性能波动或不同设备上可能出现UI不同步的问题。
  • 缺少空值判断:虽然用了weakSelf,但在转换为strongSelf后没有做空判断,若self已提前释放,会触发空指针调用。

二、规范修正后的代码

__weak typeof(self) weakSelf = self;

dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
    __strong typeof(self) strongSelf = weakSelf;
    if (!strongSelf) return; // 增加空判断,避免self已释放时执行无效操作
    
    [strongSelf presentViewController:strongSelf.coverVC animated:NO completion:^{
        [strongSelf showWindowWithImage:NO];
        
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            // 直接复用外层的strongSelf,无需重新声明
            [strongSelf dismissViewControllerAnimated:YES completion:^{
                strongSelf.coverVC = nil;
                [strongSelf hideWindow];
            }];
        });
    }];
});

三、进一步优化方向

  1. 替换固定延迟为生命周期监听:尽量避免依赖dispatch_after的硬编码延迟,可通过监听coverVC的viewDidAppear:事件来触发后续的dismiss操作,这样能更精准地匹配UI渲染完成的时机。
  2. 封装流程逻辑:将这段启动拆分为独立方法,提升代码可读性和可维护性:
- (void)executeStartupFlow {
    __weak typeof(self) weakSelf = self;
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        __strong typeof(self) strongSelf = weakSelf;
        if (!strongSelf) return;
        [strongSelf _presentCoverViewController];
    });
}

- (void)_presentCoverViewController {
    [self presentViewController:self.coverVC animated:NO completion:^{
        [self showWindowWithImage:NO];
        [self _scheduleDismissCoverViewController];
    }];
}

- (void)_scheduleDismissCoverViewController {
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        [self dismissViewControllerAnimated:YES completion:^{
            self.coverVC = nil;
            [self hideWindow];
        }];
    });
}
  1. 统一strongSelf的使用:在最外层block中声明一次strongSelf并做空判断,后续所有嵌套block直接复用这个变量,既避免循环引用,又保证操作期间self的有效性,这部分核心逻辑是符合Objective-C内存管理规范的。

内容的提问来源于stack exchange,提问作者SAHM

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 02:20:04