2011-01-24 42 views
2

我想創建NSInvocationOperation選擇這樣,它應該調用對象的方法使用參數NSInvocationOperation定義使用參數

- (void) getImages: (NSRange) bounds 
{ 
    NSOperationQueue *queue = [NSOperationQueue new]; 
    NSArray * params = [NSArray arrayWithObjects: 
      [[NSNumber alloc] initWithInt: bounds.location], 
      [[NSNumber alloc] initWithInt: bounds.length]]; 
    NSInvocationOperation *operation = [[NSInvocationOperation alloc] initWithTarget:self 
        selector:@selector(loadImagesWithOperation) 
        object:params]; 

    [queue addOperation:operation]; 
    [operation release]; 

} 

- (void) loadImagesWithOperation:(NSArray*)bounds { 
NSLog(@"loadImagesWithOperation"); 
} 

此代碼與EXC_BAD_ACCESS崩潰。如果我改變這個功能的定義

- (void) loadImagesWithOperation { 
NSLog(@"loadImagesWithOperation"); 
} 

一切都會好起來的。我試圖使用@selector的代碼塊,如@selector(loadImagesWithOperation :)@selector(loadImagesWithOperation:bounds :),但未成功。

用params來定義選擇器和函數的正確方法是什麼?

感謝。

+0

發佈崩潰的回溯 – bbum 2011-01-25 17:41:30

回答

4

正確的方法來定義一個SEL接受參數是使用一個冒號(":")字符的每個參數,所以在你的情況下,選擇應該是這樣的:

@selector(loadImagesWithOperation:) 

所以,你NSInvocationOperation對象應該初始化是這樣的:

NSInvocationOperation *operation = [[NSInvocationOperation alloc] initWithTarget:self 
       selector:@selector(loadImagesWithOperation:) 
       object:params]; 

哦,就像一個側面說明,你有你的NSArray的初始化的內存泄漏getImages:

NSArray * params = [NSArray arrayWithObjects: 
     [[NSNumber alloc] initWithInt: bounds.location], 
     [[NSNumber alloc] initWithInt: bounds.length]]; 

此補充說,已經有1一個retainCount因爲你使用+alloc對象,所以當他們被添加到NSArray,它們會發出-retain消息,從而遞增retainCount2

當這個NSArray被釋放時,這些對象將不會被釋放,因爲它們的retainCount將是1而不是0

有三種解決這個問題:

  1. 發送autorelease消息給這些對象,他們被添加到NSArray之前。
  2. 使用NSNumbernumberWithInt:類方法獲取自動發佈的NSNumber對象。
  3. 創建對這些NSNumber對象的引用,將它們添加到NSArray,然後在添加後向它們發送-release消息。
+0

感謝您的快速回答,雅各布,但在某些情況下,此代碼不起作用。選擇器中的ame仍然會導致EXC_BAD_ACCESS。我被困。 – duganets 2011-01-24 23:03:29

3

一切都很好。我曾嘗試 以使用@選擇的 代碼塊不同的語法像 @selector(loadImagesWithOperation :) 和 @selector(loadImagesWithOperation:邊界:), 但沒有成功。

initWithTarget:selector:object:需要一個選擇器,只能接受0或1個參數,不能多於(不是兩個)。這一個論點必須是一個對象。如果您需要更多參數,請使用塊或重構您的代碼(將數組與其他對象一起傳遞是一個潛在的解決方案,是的 - 有點像您在代碼中所做的事情(儘管注意內存泄漏)

崩潰是無關的,你已經顯示的代碼。發佈崩潰。

還要注意的是在頭部與get方法在可可/ iOS的一個非常特殊的意義,而不是用於這種模式。我建議loadImages