2012-09-17 2 views
0

enter image description here메모리가 부족한 후 앱이 닫힙니다. Instruments의 스크린 샷

이것은 계측기를 통해 앱을 실행할 때 얻는 것입니다. 핵심 데이터를 많이 처리하고 있습니다. 나는 이것이 분명히 옳지 않다는 것을 알 수 있지만이 스크린 샷이 무엇을 말하고 있는지 정말로 알지 못합니다. 무엇이 문제인 것처럼 보입니까? 내가 조언을 (내가 위에서 편집 한) @autoreleasepools에 포장, 여기에 주어진 다음, 그것은 여전히 ​​후 추락 :

NSFetchRequest *oldFetchRequest = [[NSFetchRequest alloc] init]; 
    NSEntityDescription *oldEntryEntity = [NSEntityDescription entityForName:@"Entry" 
                 inManagedObjectContext:oldContext]; 

    [oldFetchRequest setEntity:oldEntryEntity]; 

    int numberOfEntries = [oldContext countForFetchRequest:oldFetchRequest error:nil]; 

    int batchSize = 4; 
    [oldFetchRequest setFetchLimit:batchSize]; 
    int offset = 0; 

    while (numberOfEntries - offset > 0) { 
     @autoreleasepool { 
     [oldFetchRequest setFetchOffset:offset]; 
     NSError *error; 
     NSArray *entries = [oldContext executeFetchRequest:oldFetchRequest error:&error]; 

     for (NSManagedObject *entry in entries) { 
     @autoreleasepool { 
      Entry *newEntry = [NSEntityDescription insertNewObjectForEntityForName:@"Entry" 
                  inManagedObjectContext:newContext]; 

      newEntry.entryID = [entry valueForKey:@"entryID"]; 

      NSMutableOrderedSet *newMediaSet = [[NSMutableOrderedSet alloc] init]; 

      NSOrderedSet *mediaSet = [entry valueForKey:@"media"]; 

      int i = 0; 

      for (NSManagedObject *media in mediaSet) { 

       Media *newMedia = [NSEntityDescription insertNewObjectForEntityForName:@"Media" 
                   inManagedObjectContext:newContext]; 

       newMedia.isInPhotoLibrary = [media valueForKey:@"isInPhotoLibrary"]; 
       newMedia.positionInEntry = [NSNumber numberWithDouble:i + 1]; 

       MediaImageData *imageData = [NSEntityDescription insertNewObjectForEntityForName:@"MediaImageData" 
                      inManagedObjectContext:newContext]; 

       imageData.data = [media valueForKey:@"originalImage"]; 

       newMedia.imageData = imageData; 

       newMedia.entry = newEntry; 
       [newMediaSet addObject:newMedia]; 

       i++; 
      } 

      newEntry.media = newMediaSet; 


     } 
     } 

     [newContext save:&error]; 

     offset = offset + batchSize; 
    } 
} 

편집 : 당신이 관심이 있다면, 코드, 응축이있다

http://cl.ly/image/1U2T2p3w1X2Z

그것은 분명 처음보다는 코드로 더 있어요,하지만 여전히 충돌하는 것이 일어났다.

+0

중요한 코드를 제거하지 마십시오. 그러면 우리는 무슨 일이 일어나고 있는지 추측해야합니다. 가져 오기 요청이 올바르게 설정되지 않았습니다. 또한, autoreleasepool을 어디에 추가했는지는 알지 못합니다 ... 데이터베이스의 크기가 얼마나 큽니까? 미디어 세트와 미디어 세트에 포함 된 이미지의 크기는 어느 정도입니까? 어디서나 물건을 들고 있습니까? 당신은 문맥을 전혀 제거하고 있습니까? –

+0

나는 지금 autoreleasepools를 넣었다. 미디어 세트의 이미지는 표준 이미지의 크기이며, 사진에 따라 각각 약 1MB로 추측됩니다. 위의 코드 밖에서는 아무 것도하지 않습니다. 나는 맥락을 없애지 않을거야. – Andrew

답변

1

@autoreleasepool에 빠른 열거 형 (for 루프)의 내부를 래핑 해보십시오. 그러면 도움이 될 것입니다. 변경 사항이 위험한 메모리 소비에 도달하면 루프 내부에서 컨텍스트를 저장하기 위해 일종의 카운터를 실행할 수도 있습니다.

물론 많은 개체가 있지만 데이터 구조를 최적화하는 것이 좋습니다.

2

코드 효율을 논의하지 않고 :
외부 (while) 및 내부 (for) 루프 모두에 코드를 @autoreleasepool {}으로 묶습니다.
그렇지 않으면 많은 양의 메모리를 할당하고 바깥 쪽 이벤트 루프가 끝날 때만 해제하는 것입니다.

+0

고마워, 나는 그것을 시도 할 것이다. 내 코드의 효율성을 논의 할 수 있습니까? 나는 그것을 더 잘 만들 수있는 방법을 알고 싶어합니다. – Andrew

1

먼저, 핵심 데이터 관련 질문 게시에 관한 약간의 조언. 너무 많은 정보가 거의 없습니다. 세부 사항을 생략하면 가능한 많은 상호 작용이 있기 때문에 사람들이 당신을 도울 수 없습니다.

게시 한 코드를 보면 너무 많은 질문이 남습니다.

정보의 할당량이 아닌 전체 크기별로 정보를보고 싶습니다. 그러면 메모리가 사용되는 위치를 더 쉽게 알 수 있습니다. 그것이 그렇듯이, 나는 그 그림에서 기억이 사용 된 곳을 볼 수 없다 (다시 - 오래된 눈 - 내가 그것을 크게 할 때, 너무 흐리게 보인다).

핵심 데이터와 관련이 있다고 생각한다면 핵심 데이터 계측기를 실행하지 않는 이유는 무엇입니까?

진단 지원으로 설정합니다.

새 MOC가 PSC에 직접 연결되어 있거나 상위 MOC가 있습니까? 부모 MOC가있는 경우 저장은 상위 MOC로 밀려나 저장이 데이터베이스에 유지 될 때까지 메모리에 남아 있습니다.

mediaSet에 몇 개의 항목이 있습니까? 기억을 씹을 수있는 많은 것들이있을 수 있습니다.

FetchRequest 및 MOC에 적용한 매개 변수는 무엇입니까? 이러한 옵션에 따라 MOC는 객체를 보유 할 수 있습니다. 이를 확인하는 방법은 각 MOC에 대해 보유/삽입/삭제 된/etc 세트의 수를 기록하는 것입니다. 로깅함으로써 MOC가 당신이해야한다고 생각하지 않는 것들을 잡고 있는지 알 수 있습니다.

그러면 MOC를 새로 고침/재설정해야하는지 알 수 있습니다.

저장 후 속임수를 쓰고 [moc reset]으로 전화를 걸 수 있습니다.하지만 기억하기 전이나 후에 번호를 확인하는 것이 좋을 수 있습니다.

더 많은 디버깅을 수행하십시오. 올바른 결정을 내릴 수 있도록 더 많은 정보를 제공하십시오. 그러면 도움이되는 정보를 얻을 수 있습니다.

편집

Oooops. 나는 아마도 너무 많은 기억이 아닌 것에 대한 의견을 삭제했다. 내 나이 들었던 눈은 나에게 그 이미지의 작은 글씨를 보지 못하게했다.

편집

감사합니다. 보유/삽입/삭제 된 세트의 수를 기록하려면 어떻게해야합니까? 각 MOC에 대해? - 앤드류

상무부 해당 카테고리 매칭 오브젝트의 세트를 제공하는 여러 속성 (registeredObjects, insertedObjects, deletedObjects, updatedObjects)을 갖는다. 간단히 NSLog 각 범주에있는 개체의 개수. 각 MOC에 대해 MOC가 시간 경과에 따라 추적하고있는 객체의 수를 볼 수 있습니다.

또한 핵심 데이터 도구를 사용하십시오. 그들은 정말로 유익합니다.

+0

감사합니다. 각 MOC에 대해 보유/삽입/삭제 된 개수를 기록하려면 어떻게합니까? – Andrew