Mam niektóre rekursywny kod blokowy w celu-c, który powoduje błąd EXC_BAD_ACCESS.Objective-c rekursywne bloki z wątkami EXC_BAD_ACCESS
- (void) doSomethingWithCompletion:(void (^)())completion {
if (completion) {
dispatch_async(dispatch_get_main_queue(), completion);
}
}
- (void) testBlocks {
NSString *testString = @"hello";
__block NSInteger count = 0;
__block __weak void (^weak_block)(NSString *);
void(^strong_block)(NSString *);
weak_block = strong_block = ^(NSString *str) {
[self doSomethingWithCompletion:^{
NSLog(@"number: %zd", count);
if (++count < 10) {
weak_block(str);
}
}];
};
strong_block(testString);
}
Błąd występuje na słabym bloku (str), który zakładam, ponieważ został zwolniony po wywołaniu funkcji dispatch_async. Wywołanie strong_block (STR) w to miejsce, gdy jest zadeklarowana z __block tak:
__block void(^strong_block)(NSString *);
Powoduje ostrzeżenie strong_block „przechwytywanie«»zdecydowanie w tym bloku jest prawdopodobne, aby doprowadzić do zatrzymania cyklu”.
Więc zmieniłem metodę testBlock nie używać słabe odniesienie tak:
- (void) testBlocks {
NSString *testString = @"hello";
__block NSInteger count = 0;
__block void (^inner_block)(NSString *);
void(^strong_block)(NSString *);
inner_block = strong_block = ^(NSString *str) {
[self doSomethingWithCompletion:^{
NSLog(@"number: %zd", count);
if (++count < 10) {
inner_block(str);
}
}];
};
strong_block(testString);
}
Ale jestem pewien, czy to powoduje, że zachowują cykl czy dodanie
__block void (^inner_block)(NSString *) = weak_block;
wewnątrz bloku zamiast spowoduje również cykl zatrzymania. Jaki jest właściwy sposób radzenia sobie z tą sytuacją?
Mój mózg boli od patrzenia na to .. –