美文网首页
NSTimer如何使用

NSTimer如何使用

作者: the宇亮 | 来源:发表于2025-02-11 00:00 被阅读0次

NSTimer 是 iOS 和 macOS 开发中常用的定时器类,用于在指定的时间间隔后执行某个任务。它可以用来执行一次性任务或重复性任务。以下是 NSTimer 的基本用法和常见场景。

1. 创建 NSTimer

NSTimer 提供了多种创建方式,可以根据需求选择合适的方式。

1.1 使用 scheduledTimerWithTimeInterval:target:selector:userInfo:repeats: 方法

这是最常用的方式之一,它会自动将定时器添加到当前的运行循环中。

// 创建一个定时器,每隔1秒调用一次 target 的 selector 方法
NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:1.0
                                                  target:self
                                                selector:@selector(timerFired:)
                                                userInfo:nil
                                                 repeats:YES];
  • timeInterval: 定时器触发的时间间隔(以秒为单位)。
  • target: 定时器触发时调用方法的对象。
  • selector: 定时器触发时调用的方法。
  • userInfo: 可选的用户信息,可以传递给定时器。
  • repeats: 是否重复触发。如果为 YES,定时器会重复触发;如果为 NO,定时器只触发一次。

1.2 使用 timerWithTimeInterval:target:selector:userInfo:repeats: 方法

这种方式不会自动将定时器添加到运行循环中,你需要手动将其添加到运行循环。

NSTimer *timer = [NSTimer timerWithTimeInterval:1.0
                                         target:self
                                       selector:@selector(timerFired:)
                                       userInfo:nil
                                        repeats:YES];

// 手动将定时器添加到当前运行循环
[[NSRunLoop currentRunLoop] addTimer:timer forMode:NSDefaultRunLoopMode];

1.3 使用 scheduledTimerWithTimeInterval:invocation:repeats: 方法

这种方式使用 NSInvocation 对象来指定要调用的方法。

NSMethodSignature *signature = [self methodSignatureForSelector:@selector(timerFired:)];
NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:signature];
[invocation setTarget:self];
[invocation setSelector:@selector(timerFired:)];

NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:1.0
                                              invocation:invocation
                                                 repeats:YES];

1.4 使用 scheduledTimerWithTimeInterval:block:repeats: 方法(iOS 10+)

从 iOS 10 开始,NSTimer 提供了基于 block 的 API,使得代码更加简洁。

NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:1.0
                                                 repeats:YES
                                                   block:^(NSTimer * _Nonnull timer) {
    NSLog(@"定时器触发");
}];

2. 停止定时器

可以通过调用 invalidate 方法来停止定时器并将其从运行循环中移除。

[timer invalidate];

一旦调用了 invalidate,定时器将不再触发,并且不能再重新启动。如果你需要重新启动定时器,必须创建一个新的 NSTimer 实例。

3. 定时器触发的方法

定时器触发时会调用指定的 selectorblock。如果是 selector 方式,方法签名必须符合以下格式:

- (void)timerFired:(NSTimer *)timer {
    NSLog(@"定时器触发");
}

4. 注意事项

  • 线程问题: NSTimer 默认会在创建它的线程的运行循环中运行。如果你在后台线程中创建了定时器,确保该线程的运行循环正在运行,否则定时器不会触发。

  • 内存管理: 如果 NSTimer 持有对 target 的强引用,可能会导致循环引用。为了避免这种情况,可以使用弱引用或者在适当的时候调用 invalidate 来释放定时器。

  • 精确性: NSTimer 并不是绝对精确的,尤其是在主线程上运行时,可能会受到其他任务的影响。如果需要高精度的定时器,可以考虑使用 CADisplayLink 或 GCD 的 dispatch_source_t

5. 示例代码

#import <Foundation/Foundation.h>

@interface MyClass : NSObject

@property (nonatomic, strong) NSTimer *timer;

- (void)startTimer;
- (void)stopTimer;
- (void)timerFired:(NSTimer *)timer;

@end

@implementation MyClass

- (void)startTimer {
    self.timer = [NSTimer scheduledTimerWithTimeInterval:1.0
                                                  target:self
                                                selector:@selector(timerFired:)
                                                userInfo:nil
                                                 repeats:YES];
}

- (void)stopTimer {
    [self.timer invalidate];
    self.timer = nil;
}

- (void)timerFired:(NSTimer *)timer {
    NSLog(@"定时器触发 %@", timer.userInfo);
}

@end

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        MyClass *myClass = [[MyClass alloc] init];
        [myClass startTimer];
        
        // 让程序运行一段时间
        [[NSRunLoop currentRunLoop] runUntilDate:[NSDate dateWithTimeIntervalSinceNow:5]];
        
        [myClass stopTimer];
    }
    return 0;
}

总结

NSTimer 是一个非常有用的工具,适合用于定时任务。你可以根据需求选择不同的创建方式,并注意定时器的生命周期管理和线程问题。

相关文章

  • NSTimer的循环引用

    NSTimer基本使用 NSTimer与RunLoop NSTimer 循环引用的问题 如何在子线程使用NSTim...

  • iOS如何安全而又优雅的使用NSTimer

    如何安全而又优雅的使用一个NSTimer❓请往下看? 使用NSTimer最大的困扰就是在于必须手动释放掉这个被我们...

  • iOS-NSTimer-循环引用问题

    在使用NSTimer的时候,NSTimer会生成指向其使用者的引用,而其使用者如果也引用了NSTimer,那么就会...

  • NSTimer的使用

    NSTimer 的使用 为什么会写NSTimer呢? 原因很简单, 这里有坑! NSTimer 使用的顺序 创建N...

  • 内存管理总结

    CADisplayLink、NSTimer使用注意 CADisplayLink、NSTimer会对target产生...

  • Objective-C基础-内存管理

    1、CADisplayLink、NSTimer使用 CADisplayLink、NSTimer会对target产生...

  • CADisplayLink、NSTimer使用注意

    CADisplayLink、NSTimer使用注意 CADisplayLink、NSTimer会对target产生...

  • 底层-内存管理

    CADisplayLink、NSTimer使用注意 CADisplayLink、NSTimer会对target产生...

  • 内存管理

    CADisplayLink、NSTimer使用注意 CADisplayLink、NSTimer会对target产生...

  • iOS内存管理

    CADisplayLink、NSTimer使用注意 CADisplayLink、NSTimer会对target产生...

网友评论

      本文标题:NSTimer如何使用

      本文链接:https://www.haomeiwen.com/subject/rbvtpjtx.html