博客
关于我
performSelector系列方法的研究
阅读量:591 次
发布时间:2019-03-11

本文共 1692 字,大约阅读时间需要 5 分钟。

在开发中,当我们想要在运行时立即执行某个方法时,通常会调用NSObject的performSelector:方法。虽然这一方法很方便,但也有潜在的问题需要注意。

首先,performSelector:方法的关键在于它是在当前线程的runloop中执行的,并且默认的runloop mode是NSDefaultRunLoopMode。这种方式具有高度的动态性,但也带有一些缺点。例如:

  • 内存泄漏风险:调用者不对performSelector返回的对象负责,尤其是当调用方法如alloc、new、copy等时,系统会开辟内存空间但无法保证内存的正确管理。这会导致内存泄漏。

  • 动态方法的潜在问题:由于performSelector的Selector不确定,编译器无法有效校验方法的返回类型,这也会产生编译警告。

  • 接下来,我们可以了解如何最好地使用performSelector方法,以及如何解决这些潜在问题。

    解决方法一:替代思路,避免使用performSelector

  • 使用NSInvocation:通过动态的方式构造一个NSInvocation对象来执行方法。这种方法可以避免内存泄漏问题。

    SEL sel = NSSelectorFromString(@"new");NSMethodSignature *method = [[self class] instanceMethodSignatureForSelector:sel];NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:method];[invocation setSelector:sel];[invocation setTarget:self];[invocation invoke];
  • 使用块重构代码:可以采用代码块的方式来实现动态方法调用。

  • 使用UIApplication的sendAction方法:这是一种更简便的方式,可以在主线程上发送动态方法。

    [UIApplication.sharedApplication sendAction:NSSelectorFromString(@"new") to:self from:nil forEvent:nil];
  • 解决方法二:使用CFBridgingRelease解决内存泄漏

    当使用performSelector传递 Selector或对象时,特别是涉及 Construc累方法,及时释放内存可以避免内存泄漏。通过使用CFBridgingRelease,可以强制释放内存。

    id obj = CFBridgingRelease(((void *(*)(id, SEL))[self methodForSelector:NSSelectorFromString(@"new")])(self, NSSelectorFromString(@"new")));

    performSelector的底层实现

    performSelector的底层实现主要依赖于objc_msgSend。通过查看NSObject的源码可以发现,该方法会在runloop中执行Selector,直到找到匹配的方法。如果Selector不再存在于类中,会触发运行时错误。

    扩展1:performSelector的延迟执行

    performSelector还可以用于延迟执行任务。通过在runloop中设置计时器,可以将任务推迟到某个时间点执行。

    扩展2:performSelector的模式控制

    performSelector还支持指定特定runloop模式来执行任务,这可以让任务执行时更加精确。

    扩展3:线程控制

    performSelector还支持在其他线程执行任务,这对于需要跨线程通信的场景非常有用。

    通过以上方法,我们可以更安全、灵活地使用performSelector进行动态方法调用,同时尽量避免内存泄漏和其他潜在问题。

    如果对这一系列方法的实现细节感兴趣,可以参考相关的官方文档和源码分析。

    转载地址:http://dlttz.baihongyu.com/

    你可能感兴趣的文章
    nginx最最最详细教程来了
    查看>>
    Nginx服务器---正向代理
    查看>>
    Nginx服务器上安装SSL证书
    查看>>
    Nginx服务器基本配置
    查看>>
    Nginx服务器的安装
    查看>>
    Nginx标准配置文件(包括反向代理、大文件上传、Https证书配置、文件预览等)
    查看>>
    Nginx模块 ngx_http_limit_conn_module 限制连接数
    查看>>
    Nginx模块 ngx_http_limit_req_module 限制请求速率
    查看>>
    nginx添加允许跨域header头
    查看>>
    nginx添加模块与https支持
    查看>>
    nginx状态监控
    查看>>
    Nginx用户认证
    查看>>
    Nginx的location匹配规则的关键问题详解
    查看>>
    Nginx的Rewrite正则表达式,匹配非某单词
    查看>>
    Nginx的使用总结(一)
    查看>>
    Nginx的使用总结(三)
    查看>>
    Nginx的使用总结(二)
    查看>>
    Nginx的使用总结(四)
    查看>>
    Nginx的可视化神器nginx-gui的下载配置和使用
    查看>>
    nginx的平滑升级方法:
    查看>>