2012-06-11 3 views
2

iCloud 동기화가있는 프로젝트가 있지만 올바르게 작동하지 않습니다. 처음에는 변경된 객체 배열을 얻은 다음 CSV 문자열 (클라우드의 UIDocuments 내용이 될 것임)로 변환 한 다음이를 iCLoud에 업로드합니다. 400 개 미만의 개체가있는 경우 모든 항목이 정상이지만 더 많은 정보가 있으면 응용 프로그램이 중지됩니다.iCloud 용 UIDocuments의 큰 배열

로컬 autorelease 풀을 사용해 보았습니다. 큰 배열을 작은 배열로 분할했습니다. 그러나 도움이되지 않았습니다.

많은 UIDocument를 iCloud에 업로드하는 가장 좋은 방법은 무엇입니까? 내 업로드 방법 : 내 영어 사전과 유감의

- (void)pushChangesToCloud:(NSArray *)changedObjects { 

    for (ObjectClass *someObject in changedObjects) { 
     NSURL *pathToSyncDoc = [[self urlForDocumentsFolderIniCloud] URLByAppendingPathComponent:someObject.name]; 

     CustomUIDocument *syncDoc = [[[CustomUIDocument alloc] initWithFileURL:pathToSyncDoc] autorelease]; 
     // converting object to CSV string 
     NSString *csvContents = [SomeClass convertObjectToCSV:someObject];  
     syncDoc.documentContent = csvContents; 

     [syncDoc saveToURL:[syncDoc fileURL] 
      forSaveOperation:UIDocumentSaveForCreating 
     completionHandler:^(BOOL success) { 
      if (success) { 
       NSLog(@"YAY!"); 
      } else { 
       NSLog(@" D: "); 
      } 
     }]; 
    } 
} 

감사합니다.

+0

당신은'retain' /'release'와 수동 메모리 관리를 시도? – Eimantas

+0

@Eimantas, 대답 해줘서 고마워. 예, 원래이 방법으로 수행되었습니다. 하지만 많은 양의 데이터가있는 버그가 발생하면 autorelease 및 로컬 autorelease 풀을 사용하여 구현해야한다고 결정했습니다. –

+0

내가 생각할 수있는 또 다른 원인은 백그라운드 처리 (예 : 저장)에 사용 된 큐가 모든 개체와 그것은 충돌을 일으킬 수 있습니다. 자신의 시리얼 큐를 사용하여 저장 코드를 다시 구현할 수 있습니다. – Eimantas

답변

1

@Eimantas 덕분에 마침내 문제가 해결되었습니다. 그는 과부하 대기열에 대해 옳았습니다. "saveToUrl : forSaveOperation : completionHandler :"는 I/O 작업이므로 대기열은 (각 UIDocument에 대해) 많은 스레드를 생성하고 응용 프로그램이 중단됩니다.

- (void)saveToURL:(NSURL *)url forSaveOperation:(UIDocumentSaveOperation)saveOperation completionHandler:(void (^)(BOOL))completionHandler { 
NSError *contentsError = nil; 
NSError *attributesError = nil; 
NSError *savingError = nil; 

[self writeContents:[self contentsForType:self.fileType error:&contentsError] andAttributes:[self fileAttributesToWriteToURL:url forSaveOperation:saveOperation error:&attributesError] safelyToURL:url forSaveOperation:saveOperation error:&savingError]; 

NSLog(@"SAVING ERRORS: contents error - %@, attributes error - %@, saving error - %@",[contentsError localizedDescription], [attributesError localizedDescription], [savingError localizedDescription]); 
} 

가 그럼 난 모든 작업을 저장 실행하기 위해 내 자신의 시리얼 큐를 사용 : UIDocument가 (동시 스레드에서 문서를 저장하지 않도록) 내 사용자 지정의 방법 "forSaveOperation : completionHandler saveToUrl를"

나는 오버로드되었습니다. 를 해제 한 후

dispatch_async(mySyncQueue, ^{ 
    // do saving stuff 
}); 

과 :

myCustomQueue = dispatch_queue_create("com.whatever.MyAwesomeQueue", DISPATCH_QUEUE_SERIAL); 

절약을 위해 사용 : 다음 초기화 방법을 만들

dispatch_queue_t mySerialQueue; 

을 : 처음에는 , 당신은 바르처럼 추가해야 dealloc에서 :

dispatch_release(mySyncQueue); 

이 변경 후 아무런 문제가 없습니다.

희망이 도움이됩니다. (내 영어로는 유감 :>)

1

드미트리, saveToURL을 (을) 재정의하는 방법은 안전하지 않습니다. UIDocument saveToURL의 기본 구현은 파일 조정을 사용하여 ubiquity 데몬이 디스크에 기록 할 내용을 언제나 알고 있는지 확인합니다. writeContents에서 파일 조정을하지 않으면 구현시 파일 조정이 필요하지 않습니다. https://developer.apple.com/library/ios/documentation/UIKit/Reference/UIDocument_Class/UIDocument/UIDocument.html#//apple_ref/occ/instm/UIDocument/saveToURL:forSaveOperation:completionHandler :

은 UIDocument의 saveToURL의 문서의 토론 섹션을 참조하십시오