使用NSTimer的类

#import "TBTimerTestObject.h"
#import "TBWeakTimerTarget.h" @interface TBTimerTestObject() @property (nonatomic, weak) NSTimer *timer; @end @implementation TBTimerTestObject - (void)dealloc
{
NSLog(@"timer is dealloc");
} - (id)init
{
self = [super init]; if (self) {
TBWeakTimerTarget *timerTarget =[[TBWeakTimerTarget alloc] initWithTarget:self andSelector:@selector(timerDidFire:)]; _timer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:timerTarget selector:@selector(timerDidFire:) userInfo:nil repeats:YES];
}
return self;
} - (void)timerDidFire:(NSTimer*)timer
{
NSLog(@"%@", @"");
} @end

target类:

头文件:

#import <Foundation/Foundation.h>

@interface TBWeakTimerTarget : NSObject

- (instancetype) initWithTarget: (id)target andSelector:(SEL) selector;
- (void)timerDidFire:(NSTimer *)timer; @end

m文件:

#import "TBWeakTimerTarget.h"

@implementation TBWeakTimerTarget
{
__weak id _target;
SEL _selector;
} - (instancetype) initWithTarget: (id) target andSelector: (SEL) selector
{
self = [super init];
if (self) {
_target = target;
_selector = selector;
}
return self;
} - (void) dealloc
{
NSLog(@"TBWeakTimerTarget dealloc");
} - (void)timerDidFire:(NSTimer *)timer
{
if(_target)
{
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Warc-performSelector-leaks"
[_target performSelector:_selector withObject:timer];
#pragma clang diagnostic pop
}
else
{
[timer invalidate];
}
}
@end

使用示范:

@interface ViewController ()

@property (nonatomic, strong) TBTimerTestObject *obj;

@end

@implementation ViewController

- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
} - (IBAction)tap:(id)sender
{
NSLog(@"tappp"); self.obj = [[TBTimerTestObject alloc] init]; [self performSelector:@selector(timerDidFired:) withObject:nil afterDelay:];
} - (void)timerDidFired:(NSTimer *)timer
{
self.obj = nil;
NSLog(@"AppDelegate timerDidFired");
} @end

打印log:

-- ::40.120 XIBTest[:] tappp
-- ::41.121 XIBTest[:]
-- ::42.121 XIBTest[:]
-- ::43.121 XIBTest[:]
-- ::43.122 XIBTest[:] timer is dealloc
-- ::43.122 XIBTest[:] AppDelegate timerDidFired
-- ::44.121 XIBTest[:] TBWeakTimerTarget dealloc

具体参考了:

http://stackoverflow.com/questions/16821736/weak-reference-to-nstimer-target-to-prevent-retain-cycle

国内某些说在dealloc中写:

timer.invalid;

timer = nil;

是不行的,因为循环引用了,都不会进入dealloc方法中。具体可以自己试试。

iOS 里面 NSTimer 防止 循环引用的更多相关文章

  1. iOS 容易引“起循环引用”的三种场景

    笔者在阅读中总结了一下,在iOS平台容易引起循环引用的四个场景: 一.parent-child相互持有.委托模式 [案例]:   @interface FTAppCenterMainViewContr ...

  2. NSTimer的循环引用

    在日常开发中想到会引起循环引用的一般比较容易想起的是 1.delegate 2.block 今天要说的就是另外一个,NSTimer 这个比较容易会被忽略掉 简单的说就是创建timer为成员变量的时候t ...

  3. NSTimer解除循环引用

    NSTimer作为一个经常使用的类,却有一个最大的弊病,就是会强引用target.造成调用timer很麻烦.稍有不慎就造成内存泄漏. 下面就是为解决问题做的封装. 直接上代码: #import < ...

  4. ios block 导致的循环引用

    [[NSNotificationCenter defaultCenter] addObserverForName:@"UIWindowDidRotateNotification" ...

  5. iOS 循环引用讲解(中)

    谈到循环引用,可能是delegate为啥非得用weak修饰,可能是block为啥要被特殊对待,你也可能仅仅想到了一个weakSelf,因为它能解决99%的关于循环引用的事情.下面我以个人的理解谈谈循环 ...

  6. CADisplayLink、NSTimer循环引用解决方案

    前言:CADisplayLink.NSTimer 循环引用问题 ​ CADisplayLink.NSTimer会对Target产生强引用,如果target又对他们产生强引用,那么就会引发循环引用. @ ...

  7. iOS之weak和strong、懒加载及循环引用

    一.weak和strong 1.理解 刚开始学UI的时候,对于weak和strong的描述看得最多的就是“由ARC引入,weak相当于OC中的assign,但是weak用于修饰对象,但是他们都不会造成 ...

  8. 【转】iOS学习之容易造成循环引用的三种场景

    ARC已经出来很久了,自动释放内存的确很方便,但是并非绝对安全绝对不会产生内存泄露.导致iOS对象无法按预期释放的一个无形杀手是——循环引用.循环引用可以简单理解为A引用了B,而B又引用了A,双方都同 ...

  9. 【原】iOS容易造成循环引用的三种场景,就在你我身边!

    ARC已经出来很久了,自动释放内存的确很方便,但是并非绝对安全绝对不会产生内存泄露.导致iOS对象无法按预期释放的一个无形杀手是——循环引用.循环引用可以简单理解为A引用了B,而B又引用了A,双方都同 ...

随机推荐

  1. Android消息的提示,Toast吐司方式

    1:选中某个控件进行触发 2:触发事件进行监听,然后绑定Toast对象进行消息提示 1,创建Android项目的时候,自带的一个Activity,我们看看代码 package com.example. ...

  2. php版本引起的const问题

    刚刚遇到一个问题,类中定义了一个常量: const USER = ['aa', 'bb', 'cc']; 在类中的静态函数中调用以上常量不会出错.网站中所有的网页均能正常打开. 而当push到线上后, ...

  3. 在Spring MVC项目中,注解方式使用 .properties 文件及 UTF-8编码问题

    xml配置 <!-- 配置文件 --> <bean id="configProperties" class="org.springframework.b ...

  4. IIS上虚拟目录下站点的web.config与根站点的web.config冲突解决方法

    IIS7.5上在站点下部署虚拟目录,访问虚拟目录下的项目提示与父节点配置冲突.,节点与的<system.web>节点与主站点的<system.web>冲突解决方法: 在站点下的 ...

  5. z-index和transform

    z-index和transform是CSS中的属性,但很少同学将二者联系到一起,感觉他们八杆子打不上.事实真的是这样吗?如果你也不能确认,这篇文章就值得你花点时间阅读.因为阅读完了,你会有所收获的. ...

  6. WNDR3700V4 安装SVN Server

    下文所用路由器型号为:WNDR3700V4 参考链接:http://dd-wrt.ca/phpBB2/viewtopic.php?t=86912&highlight=optware http: ...

  7. hbuilder中如何使用egit上传项目

    刚开始使用时,我也是遵照网上的教程来的,其实就那一篇教程,到处被转载,怎么搜都是那一个,实际操作发现有点小不同,所以实际截图给大家一个参考. 1.首先肯定是进入hbuilder下载egit插件啦.(工 ...

  8. vuex2.0.0爬坑记录 -- mutations的第一个参数state不能解构

    今天在学习vuex的过程中,遇到了一个很困扰人的问题,最终利用vuex的状态快照工具logger解决了问题. 问题是这样的,我在子组件中使用了mapState()函数来将状态映射至子组件中,使子组件能 ...

  9. Google Chrome 调试

    [原文地址:http://www.cnblogs.com/QLeelulu/archive/2011/08/28/2156402.html ] 在Google Chrome浏览器出来之前,我一直使用F ...

  10. 拼sql条件时判断 是不是当前时间是不是周五,如果今天不是周五,就选上周五

    if (Request.QueryString["start"] == null) { for (int i = 0; i < 6; i++) { if (DateTime. ...