令人沮丧的NSTask和NSTaskDidTerminateNotification问题

时间:2013-07-12 00:23:10

标签: ios objective-c ipad cocoa-touch cocoa

所以为了记录,我已经在这个问题上搜索了几天。最后,我正处于困境中。我已经阅读了线程编程指南,并在谈到NSRunLoops时密切关注,我认为这可能是我想要的方向。这是问题所在:

我有一个非常简单的演示项目,它只包含一个AppDelegate和一个名为TestObj的类,在testObj中我有

@implementation TestObj

-(void)executeTheTaskWithObj:(id)sender {

NSTask *task = [[NSTask alloc] init];
[task setLaunchPath: @"/bin/sh"];
NSArray *arguments = [NSArray arrayWithObjects: @"-c", @"echo hello", nil];
[task setArguments:arguments];

    /* This works but I want to handle the notification in this class, not the senders     class */
//[[NSNotificationCenter defaultCenter] addObserver:sender    selector:@selector(taskComplete:) name:NSTaskDidTerminateNotification object:task];

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(taskComplete:) name:NSTaskDidTerminateNotification object:task];
[task launch];
}

-(void)taskComplete:(NSNotification *)notification {
NSLog(@"Task Complete");
}

这个类由我的appDelegate调用,如此

@implementation AppDelegate

- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
TestObj *myObj = [[TestObj alloc] init];
[myObj executeTheTaskWithObj:self];
}

所以问题是应用程序崩溃了“objc_msgSend()”断点证明,只要我添加“self”作为观察者,它就会爆炸。无论如何,我故意没有多线程,这只是一个普通的电话。所以我的第一次预感可能是我应该使用NSRunLoop的一个实例。所以我阅读了线程编程指南的NSRunLoop部分,它明确地说cocoa应用程序在main中自动启动了runloop。所以我不应该创建另一个吧?我不想回答这个问题,但至少有一些关于如何解决这个问题的指导。谢谢!

1 个答案:

答案 0 :(得分:1)

问题是在applicationDidFinishLaunching超出范围后,myObj正被释放。创建一个强大的属性myObj,然后它应该正常工作。

- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
    self.myObj = [[TestObj alloc] init];
    [self.myObj executeTheTaskWithObj:self];
}