Re: NSOperationQueue
Re: NSOperationQueue
- Subject: Re: NSOperationQueue
- From: John Love <email@hidden>
- Date: Sat, 13 Sep 2008 19:15:51 -0400
>>>>>
FROM : Quincey Morris
Your code is crashing because you're doing it wrong:
On Sep 13, 2008, at 05:05, John Love wrote:
> - (void) calculateWorksheet:(id)data {
> int row;
> for (row=1; row < 500; row++) {
> // long calculation here
> }
> }
>
> - (void) startQueue {
> NSLog(@"start queue"); // I see this in the debugger
> opData = @"not used data";
> theQueue = [[NSOperationQueue alloc] init];
> theOp = [[NSInvocationOperation alloc] initWithTarget:self
>
> selector:@selector(calculateWorksheet:)
> object:opData];
> [theQueue addOperation:theOp];
> }
>
> - (void) stopQueue {
> NSLog(@"stop queue"); // .. but I do not see this
> [theQueue cancelAllOperations];
> // [theQueue release]; // done by [theOp release]
> [opData release];
> [theOp release];
> }
Cancelling a NSOperation (including a NSInvocationOperation) doesn't
stop it. The operation itself must detect that it was cancelled, then
clean up and exit. So what this code effectively does is to release
'theOp' while it's still running. It's not surprising you're getting a
crash as a result.
Also, it's not clear why you think '[theOp release]' releases
'theQueue' too. Normally, you'd expect the queue to persist for the
life of your application, while the operations are created, added to
the queue and destroyed as needed. There's nothing absolutely wrong
with creating a new queue for every operation, I guess, but you are
going to have to release the queue when the operation using it is
finished.
>>>>>
Bingo! ... thank you everyone.
First, in my method -startQueue, I used:
theQueue = [[[NSOperationQueue alloc] init] autorelease];
Otherwise, Quincy is accurate ... I would have to call [theQueue
release] in -stopQueue.
But, I still have to call [opData release]. Whoopee!! The app does
not crash.
You see, I somehow "assumed" that [theQueue cancelAllOperations] would
release not only theQueue, but also opData. It seems "logical" that
it would, but I have "almost" proven that cancelAllOperations does
not .. because re-inserting the 2 releases makes the app work, well
actually using autorelease on the initialization of theQueue, coupled
with [theOp release].
At this point, I still have some "challenges"; namely,
(1) while my queue/op is percolating, I *still* don't get back control
in my app until the thread is finished; specifically, for example, I
cannot press CMD-N to get a new empty window until after the thread is
finished. Isn't that the purpose of multi-threading? I've got a nasty
feeling that somehow I have missed something big-time significant?
(2) I do all the window set-up stuff within MyDocument's -
windowControllerDidLoadNib within which I call my unique -MakeNewFile
and it is within -MakeNewFile that I then start the queue stuff.
... but the new window with the opened file's title does not
appear until after the thread is finished ... this is probably
directly related to (1) ... or maybe I'm just not calling -MakeNewFile
where it should be called, namely, somewhere other than -
windowControllerDidLoadNib.
I think I'm almost there, but I still need some help to get to the
finish line.
John Love
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden