据我了解,有几种方法可以发送要在线程中执行的任务。我最常用的是:
1) performSelector:withObject:afterDelay:
2) performSelectorOnMainThread:withObject:waitUntilDone:
3) performSelectorInBackground:withObject:
4) [NSThread detachNewThreadSelector:toTarget:withObject:]
我的第一个问题是,除了明显的参数差异之外,1) 和 2) 之间有什么区别?它们实际上是否都在主线程中工作(其自动释放池是在 main.m 中自动创建的)?我刚刚从某人在 Stackoverflow 上的帖子中读到方法 1) 实际上是在一个新线程中工作,因此应该为其选择器方法创建一个自动释放池。这个对吗?我一直在使用 1) 很多,主要是为了利用延迟参数,但我从未为它们创建自动释放池。没有发生任何灾难性的事情。
接下来,3) 和 4) 都在单独的线程中执行任务。我听说 UI 的东西不应该在这些线程中完成,但我对什么是严格的 UI 感到困惑。我试图编写代码以在表格视图从导航控制器模态启动时基本上播放重复加载动画。然后动画在 tableview 控制器的 viewDidLoad 方法中停止。最初,我只是将启动动画的代码粘贴在启动模态视图的代码行之上。发生的事情是动画从未播放过。
[[self loadingView] playAnimation];
SettingsViewController *menus = [[SettingsViewController alloc] initWithNibName:@"SettingsViewController" bundle:nil];
MyNavigationController *navController = [[MyNavigationController alloc] initWithRootViewController:menus];
[menus setParent:navController];
[navController setDelegate:self];
menus.mainViewController = self;
[self presentModalViewController:navController animated:YES];
[navController release];
[menus release];
然后我尝试了以下方法,它奏效了......
[NSThread detachNewThreadSelector:@selector(settingsOpeningThread) toTarget:self withObject:nil];
[[self loadingView] playAnimation];
- (void) settingsOpeningThread {
NSAutoreleasePool *apool = [[NSAutoreleasePool alloc] init];
SettingsViewController *menus = [[SettingsViewController alloc] initWithNibName:@"SettingsViewController" bundle:nil];
MyNavigationController *navController = [[MyNavigationController alloc] initWithRootViewController:menus];
[menus setParent:navController];
[navController setDelegate:self];
menus.mainViewController = self;
[self presentModalViewController:navController animated:YES];
[navController release];
[menus release];
[apool release];
}
动画会一直播放,直到 SettingsViewController 视图完全启动。但是启动像这样的模态视图是否算作“UI”并且应该避免?此外,每次启动模式视图时,我都会在 Instruments 中遇到一些奇怪的内存泄漏错误。但它来自那些“系统库”之一,我被告知很难调试。这里可能出了什么问题?
很抱歉这篇令人尴尬的长帖子。任何帮助将不胜感激!