2012-04-04 2 views
1

Когда я использую следующий код, мне сказали, есть утечка:Когда я использую NSRunLoop Instruments дал течь

- (void)dealloc 
{ 
    [connection release], connection = nil; 
    [responseData release],responseData = nil; 
    [cityCode release], cityCode = nil; 
    [requestUrlString release], requestUrlString = nil; 
    [returnDataDic release], returnDataDic = nil; 

    [super dealloc]; 
} 

- (id)initWithCityCode:(NSString *)aCityCode 
      requestURL:(NSString*)urlString 
      responseType:(SWEngineRequestType)theResponsetype 
       target:(id)theTarget 
       action:(SEL)theAction 
{ 
    if ((self = [super init])) 
    { 
     _isExecuting = NO; 
    _isFinished = NO; 
    target = theTarget; 
    action = theAction; 
    cityCode = [aCityCode retain]; 
     requestUrlString = [urlString copy]; 
     responseType = theResponsetype; 
     returnDataDic = [[NSMutableDictionary alloc] initWithCapacity:1]; 
     if (cityCode) 
     { 
      [returnDataDic setObject:cityCode forKey:SWEATHER_CITYCODE]; 
     } 
     [returnDataDic setObject:[NSNumber numberWithInt:responseType]  forKey:SWEATHER_DOWNTYPE]; 
    } 
    return self; 
} 


- (BOOL)isConcurrent 
{ 
return YES; 
} 


- (void)finish 
{ 

[self willChangeValueForKey:@"isExecuting"]; 
[self willChangeValueForKey:@"isFinished"]; 
_isExecuting = NO; 
    _isFinished = YES; 

[self didChangeValueForKey:@"isExecuting"]; 
[self didChangeValueForKey:@"isFinished"]; 

    [connection release], connection = nil; 
    [responseData release],responseData = nil; 
    [cityCode release], cityCode = nil; 
    [requestUrlString release], requestUrlString = nil; 
    [returnDataDic release], returnDataDic = nil; 
    done = YES; 
} 

- (BOOL)isExecuting 
{ 
return _isExecuting; 
} 

- (BOOL)isFinished 
{ 
return _isFinished; 
} 

- (void)main 
{ 
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 

    done = NO; 
    if ([self isCancelled]) 
    { 
    [self willChangeValueForKey:@"isFinished"]; 
    _isFinished = YES; 
    [self didChangeValueForKey:@"isFinished"]; 
     [pool release]; 
    return; 
} 

[self willChangeValueForKey:@"isExecuting"]; 
_isExecuting = YES; 
[self didChangeValueForKey:@"isExecuting"]; 

    NSURL * urlToDownLoad = [NSURL URLWithString:[requestUrlString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]]; 
NSURLRequest *request = [NSURLRequest requestWithURL:urlToDownLoad cachePolicy:NSURLRequestReloadIgnoringCacheData timeoutInterval:20]; 

connection = [[NSURLConnection alloc] initWithRequest:request delegate:self]; 
if (connection) 
    { 
    responseData = [[NSMutableData alloc] init]; 
     [connection start]; 
} 
    else 
    { 
    [self finish]; 
} 

    if (connection != nil) 
    { 
     do 
     { 
      [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; 
     } 
     while (!done); 
    } 

    [pool release], pool = nil; 
} 

#pragma mark - 
#pragma mark - NSURLConnectionDataDelegate methods 

- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response 
{ 
    [responseData setLength:0]; 
} 

- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data 
{ 
    [responseData appendData:data]; 
} 


- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error 
{ 
    [returnDataDic setObject:@"error" forKey:...]; 
[target performSelectorOnMainThread:action withObject:returnDataDic waitUntilDone:NO]; 
    [self finish]; 
} 

- (void)connectionDidFinishLoading:(NSURLConnection *)connection 
{ 
    [returnDataDic setObject:responseData forKey:...]; 
    [target performSelectorOnMainThread:action withObject:returnDataDic waitUntilDone:NO]; 
    [self finish]; 
} 
@end 

инструмент дал мне течь в: [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; Почему? Благодаря!

Я просто хочу иметь асинхронную загрузку при операции, но я использую NSAutoreleasePool, после чего прибор дал утечку в: [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]];.

ответ

0

Какой объект идентифицировал прибор как имеющий утечку? Где он был выделен? Какова была трассировка стека?

При запуске цикла запуска могут запускаться все источники цикла запуска и наблюдатели цикла цикла. Таким образом, эти несколько строк кода скрывают почти бесконечный набор возможных вещей, происходящих по мере запуска цикла выполнения. У любого из них может быть утечка, иначе приборы могут быть ошибочными.

Как правило, плохая идея запускать цикл выполнения в режиме по умолчанию во внутреннем цикле. Непонятно, что вы пытаетесь сделать с этим циклом, но обычно вы должны планировать любые собственные источники цикла запуска в режиме частного цикла запуска, а затем запускать цикл цикла в этом режиме. Таким образом, вы уверены, что запускаются только ваши собственные источники, которые обычно вы хотите.

+0

wo просто хочу иметь асинхронную загрузку при операции, я использую runloop, чтобы заставить операцию дождаться ответа, давшего мне ответ. благодаря мне помог. –

+0

Итак, используйте '- [NSURLConnection initWithRequest: delegate: startImmediately:]' с 'NO', поэтому он не будет автоматически назначен в режиме по умолчанию. Затем используйте '-scheduleInRunLoop: forMode:', чтобы запланировать его в приватном режиме (просто используйте произвольное имя для режима). Затем запустите цикл выполнения только в этом режиме. –

+0

Я делаю, как вы говорите, но есть также утечка в: [[NSRunLoop currentRunLoop] runMode: NSDefaultRunLoopMode beforeDate: [NSDate farFuture]], я не знаю, где у меня ошибка, но я все еще хочу поблагодарить вас. –

2

Попробуйте положить ваши

[[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; 

в autorelease бассейне.

Смежные вопросы