1

나는 이것이 100 % 안전하다고 확신하지만, 나는 무엇이든 놓치고 싶지 않다. 다음 코드가 있습니다안전합니까? 블럭에서 자아로서의 자존심을 유지할 가능성이 있음

- (void) scheduleControlSurfaceProcess { 
    [self.operationQueueForMessageProcessing addOperationWithBlock:^{ 
     // do something 
     [self scheduleControlSurfaceProcess];  
    }]; 
} 

여기서 self는 싱글 톤입니다. 블럭은 non-main-thread 쓰레드처럼 훌륭하게 작동합니다. 프로파일 러에 메모리 문제가 보이지 않습니다 (많은 부분을 신뢰하지 않습니다).

그래서 "캡처 된 개체가 강하게 보유한 개체에 의해 차단이 유지됩니까?"라는 경고를 무시할 수 있습니까? 그렇지 않다면 블록을 공개하겠다고 어떻게 주장 할 수 있습니까 (ARC 사용)? 경고가 사라지는 것은 쉽지만, id what = self을 지정하면 문제가 해결되지 않는 것처럼 보입니다.

EDIT :이 질문에서 아주 늦게 깨달은 것처럼 실제 문제는 내가 블록 자체에서 다시 일정을 조정한다는 것입니다. 이것은 각 블록이 다음 블록을 보유하기 때문에 분명히 문제가됩니다.

참고 : 내가 lots of questions on this topic이 있다는 것을 알고 있지만 어떤 경우, 상황이 유사한있는, 알 정도로 전문가가 아니에요.

답변

5
- (void) scheduleControlSurfaceProcess { 
    __weak id SELF = self; 
    [self.operationQueueForMessageProcessing addOperationWithBlock:^{ 
     id strongSelf = SELF; //Guarantee self doesn't go away in the meantime 
     // do something 
     [self.operationQueueForMessageProcessing addOperationWithBlock:^{ 
      [strongSelf scheduleControlSurfaceProcess]; 
     }]; 
    }]; 
} 

여기에는주기가 없을 것입니다. 경고는 완전히 유효하고, 자체 작업 큐를 보유하고, 큐는 블록을 보유하고, 블록은 자체를 보유합니다. 그리고 우리는 라운드 앤드 라운드.

수정 된 예제에서 블록은 SELF을 캡처하여 'strongSelf'에 저장합니다. strongSelf 단계는 반드시 필요한 것은 아니지만 블록 실행 중에 self에 대한 참조가 바뀌지 않도록합니다.

+0

+1 감사합니다. 나는 정말로 놀랐다. 그러나 그것은 충돌 로그가없는 어떤 최근의 충돌을 설명 할 것이다. BTW는 내가 4.3을 위해 여전히 구축중인 유일한 개발자이며, 그렇다면 1 월에 출시 될 응용 프로그램에 위배 되는가? 어쨌든, 4.x가'__unsafe_unretained'를 사용해야한다면, 제 생각에는 그렇습니다. 내 이해는 iPad 사용자의 50 % 이상이 4.x를 계속 사용한다는 것입니다. –

+1

모든 새로운 개발을 위해 5.0 이상을 제안합니다. 더 이상 4.x를 지원하려는 노력은 가치가 없습니다. 하지만 예, __weak를 __unsafe_unretained로 바꾸십시오. –

+0

이제 저는 정말로 혼란 스럽습니다. 내가 제안한대로 조정 한 후에도 내 블록이 확실히 새어 나옵니다. 블록 내에서 호출 된'scheduleControlSurfaceProcess' 메쏘드의 규칙은 무엇입니까? Xcode는 확실히 이것을 위해 파싱하지 않습니다. 모든 도움을 미리 감사드립니다. 더 많은 정보가없는 –