主線程不死是因爲主線程裏面有一個RunLoop,RunLoop裏面有一個do while死循環,保證了程序的不退出
那麼如果我們有一個需求,需要一直在後臺進行某個耗時操作,比如檢查聯網狀態,比如掃描用戶的某些行爲等等.
這時候肯定要在子線程進行,如果能保證一個子線程的不死,就能避免頻繁的創建與銷燬線程.
方法:
模仿主線程不死的操作
1.創建並強引用線程
2.往該線程裏添加RunLoop
3.往RunLoop裏面添加事務(source,timer,observer),保證RunLoop不退出
4.RunLoop run
這樣我們就可以隨時調用該線程處理一些任務了,代碼如下
#import "ViewController.h"
#import "GQThread.h"
@interface ViewController ()
@property (nonatomic,strong)GQThread * thread; // 重寫了dealloc方法,查看線程是夠銷燬
@end
@implementation ViewController
- (void)viewDidLoad {
[superviewDidLoad];
self.thread = [[GQThreadalloc] initWithTarget:selfselector:@selector(threadBegin1)object:nil];
self.thread.name =@"不死線程";
[self.threadstart];
}
// threadBegin123都可以讓線程不死
- (void)threadBegin1 {
@autoreleasepool{ //必須的,下面兩個方法也應該加上,處理一些autorelease對象
[[NSRunLoop currentRunLoop] addPort:[NSPortport] forMode:NSDefaultRunLoopMode];
[[NSRunLoopcurrentRunLoop] run];
NSLog(@"threadBegin");//主句代碼不會執行了,因爲[[NSRunLoopcurrentRunLoop] run]一直在跑圈,在RunLoop內部會不斷去查看該線程有沒有任務要處理,若有,就讓它處理一下
}
}
- (void)threadBegin2{
while (1) {
[[NSRunLoopcurrentRunLoop] run];
}
}
- (void)threadBegin3{
[NSTimerscheduledTimerWithTimeInterval:2.0target:selfselector:@selector(test)userInfo:nilrepeats:YES];
[[NSRunLoopcurrentRunLoop] run];
}
// 自定義的一些任務給該線程執行
- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
[selfperformSelector:@selector(test)onThread:self.threadwithObject:nilwaitUntilDone:NO];
}
- (void)test
{
NSLog(@"***********test2*******%@", [NSThreadcurrentThread]);
// NSLog(@"%@", [NSRunLoop currentRunLoop]);
}