2016-11-23 4 views
0

I Quellcode haben, wie folgend:Beenden app aufgrund nicht abgefangene Ausnahme ‚NSInternalInconsistencyException‘, Grund: ‚beginnen kann nicht in der Mitte einer Iteration Iterieren‘

+ (NSDictionary *)incrementalUpdateTask 
{ 
    __block NSDictionary *result = nil; 
    __block BOOL isFinish = NO; 
    [EQPlatformManager getIncrementTaskWithSuccess:^(NSArray *deletedList, NSArray *updateList) { 
    result  = @{@"delete":deletedList, @"update":updateList}; 
    isFinish = YES; 

    } failed:^(NSError *error) { 
     isFinish = YES; 
    }]; 
    while (!isFinish) { 
     [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode 
          beforeDate:[NSDate distantFuture]]; 
    } 
    return result; 
} 

Dieser Code-Segment Ausnahme führt, wie folgend :

0 CoreFoundation ___exceptionPreprocess + 124 
1 libobjc.A.dylib objc_exception_throw + 56 
2 CoreFoundation +[NSException raise:format:] 
3 Foundation -[NSAssertionHandler handleFailureInFunction:file:lineNumber:description:] + 88 
4 UIKit __prepareForCAFlush + 500 
5 UIKit __beforeCACommitHandler + 24 
6 CoreFoundation ___CFRUNLOOP_IS_CALLING_OUT_TO_AN_OBSERVER_CALLBACK_FUNCTION__ + 32 
7 CoreFoundation ___CFRunLoopDoObservers + 372 
8 CoreFoundation CFRunLoopRunSpecific + 476 
9 Foundation -[NSRunLoop(NSRunLoop) runMode:beforeDate:] + 304 
10 MyAPPName +[EQUtil incrementalUpdateTask] (EQUtil.m:2317) 
11 MyAPPName -[EQMainTaskViewController appDidBecomeActive] (EQMainTaskViewController.m:331) 

Diese Ausnahme tritt gelegentlich auf und ist sehr schwierig zu reproduzieren. Kann mir jemand helfen?

Antwort

0

Es ist eine Mischmasch Mischung aus synchronen und asynchronen Code.Sie haben einen Block und dann eine Schleife, aber die Schleife kann und wird vor ausführen der asynchrone Code ist abgeschlossen. Sie können einfach nicht die Schleife abhängig von dem Ergebnis des Blocks so haben. Und diese while-Schleife ist einfach schrecklich, Entschuldigung, es gibt kein anderes Wort dafür, ich will nicht unhöflich klingen, aber es zeigt Ihnen wirklich nicht weiß was los ist. Ich fordere Sie auf, viel über asychonicity und Blöcke zu lesen und verstehen beide vollständig bevor Sie etwas anderes wie dies tun.

Sie müssen die Schleife loswerden, bewegen Sie den Code, der in der Schleife innerhalb des Blocks ist. Außerdem müssen Sie die return-Anweisung loswerden, Sie können die return-Anweisung nicht dort behalten, wo sie ist, aber Sie können sie auch nicht in den Block einfügen. Sie müssen den aufrufenden Code des Ergebnisses auf asynchrone Weise benachrichtigen, indem Sie entweder einen Block an incrementalUpdateTask übergeben oder eine Benachrichtigung an den aufrufenden Code senden.

Sie haben eine Menge zu lernen.

+0

Thank you very much. Die Methode 'incrementalUpdateTask' wird im Handler von UIApplicationDidBecomeActiveNotification ausgeführt, was bedeutet, dass sie im Hauptthread ausgeführt wird. Eigentlich erwarte ich * while loop * execute ** bevor ** der asynchrone Code beendet ist. Dies bedeutet, dass der Haupt-Thread blockiert wird, bis der asynchrone Code beendet ist. Das ist genau das, was ich will. – Emalwb

+0

Sie sollten niemals einen Thread absichtlich blockieren. Was auch immer Sie versuchen, Ihre Idee zu tun, ist falsch. Es wird immer eine bessere Lösung geben. – Gruntcakes

0

Sie müssen Ihre Methodendeklaration wie folgt mit Block ändern.

- (NSDictionary *)incrementalUpdateTaskWithBlock:(void(^)(NSArray *deletedList, NSArray *updateList ,BOOL isFinish))callback 
{ 
    [EQPlatformManager getIncrementTaskWithSuccess:^(NSArray *deletedList, NSArray *updateList, BOOL isFinish) { 
     callback(deletedList ,updateList , YES);// pass parameter as your requirement 

    } failed:^(NSError *error) { 
     callback(nil ,nil , YES); // pass parameter as your requirement 
    }]; 

} 

// für get Ergebnis

-(void)getResult{ 
    [self incrementalUpdateTaskWithBlock:^(NSArray *deletedList, NSArray *updateList, BOOL isFinish) { 
     NSLog(@"deleted list : %@", deletedList); 
     if (!isFinish) { 
      // as per your need 
      // [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode 
            //beforeDate:[NSDate distantFuture]]; 
     } 
    }]; 
} 
+0

Vielen Dank. Und ich bin am Wandern, was zur Ausnahme führt. – Emalwb

Verwandte Themen