특정 개체 ID에서 Core Data 개체를 가져 오는 방법은 무엇입니까?


120

다음 코드를 사용하여 Core Data에서 개체의 ID를 쉽게 얻을 수 있습니다.

NSManagedObjectID *moID = [managedObject objectID];

그러나 특정 개체 ID를 제공하여 핵심 데이터 저장소에서 개체를 가져 오는 방법이 있습니까? 다음과 같이 NSFetchRequest를 사용하여이 작업을 수행 할 수 있다는 것을 알고 있습니다.

NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Document" inManagedObjectContext:managedObjectContext];
[fetchRequest setEntity:entity];

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(objectID = %@)", myObjectID];
[fetchRequest setPredicate:predicate];

그러나 자체 가져 오기 요청을 시작하지 않는 방식으로 수행하고 싶습니다. 어떤 아이디어?


그러나 가져 오기 요청 방법을 사용하면 속성 또는 관계를 미리 가져 오도록 설정할 수 있으므로 항목에 액세스 할 때 더 많은 쿼리가 아닌 뛰어난 효율성을 제공합니다.
malhal

답변:


208

원하는 :

-(NSManagedObject *)existingObjectWithID:(NSManagedObjectID *)objectID
                                   error:(NSError **)error

해당 ID가있는 저장소에서 개체를 가져 오거나 존재하지 않으면 nil을 가져옵니다.

(주의 : NSManagedObjectContext에는 비슷한 이름의 이름을 가진 두 가지 메서드가 있습니다.이 두 가지 방법은 다음과 같습니다.

-(NSManagedObject *)objectWithID:(NSManagedObjectID *)objectID

... 제공된 objectID를 사용하여 해당 개체가 실제로 저장소에 있는지 여부에 관계없이 오류 개체를 만듭니다 . 존재하지 않는 경우 NSManagedObjectContext의를 사용하여 먼저 객체를 삽입하지 않으면 오류를 발생시키는 모든 것이 실패합니다 insertObject:. 내가 찾은 유일한 용도는 ObjectID를 유지하면서 저장소에서 저장소로 개체를 복사하는 것입니다.

-(NSManagedObject *)objectRegisteredForID:(NSManagedObjectID *)objectID

... 이 managedObjectContext에 의해 저장소에서 가져온 경우 해당 ID를 가진 개체를 반환합니다 . 이 방법이 유용하다는 것을 아는 사람이 있으면 의견을 말하십시오.)

[eta .: 첫 번째 방법과 다른 두 방법의 또 다른 중요한 차이점은 existingObjectWithID:error:오류를 반환하지 않는다는 것입니다. 항상 전체 개체를 가져옵니다. 이를 피하려는 경우 (예 : 큰 blob 속성을 사용하여 가져 오기 비용이 많이 드는 객체로 작업) 오류를 발생시키지 않는 objectWithID:or 를 사용하여 영리해야합니다 objectRegisteredForID:. 또는 적절하게 구성된 가져 오기 요청을 사용합니다.]


11
-(NSManagedObject *)objectRegisteredForID:(NSManagedObjectID *)objectID객체가 이미 컨텍스트에 존재하는지 확인하고 가져오고 싶지 않을 때 유용합니다.
Tony

내 상황. 에 -tableView:didSelectRowAtIndexPath: UIAlertView 예에 / 아무 표시되지 않습니다. "예"에서-개체에 대한 작업이 있습니다. NSFetchedResultsController원격에서 + 백그라운드 CoreData 업데이트를 사용 합니다. 따라서 개체를 저장할 수 없습니다. 경고가 화면에 표시되는 동안 저장소를 업데이트하고 개체를 제거 할 수 있습니다. objectId를 저장 한 다음 경고 대리자에서 한 번 더 검색합니다. 내가 사용하기 때문에 NSFetchedResultsController-필요한 모든 객체는 이미이 순간까지 맥락에 있습니다. 또한 컨텍스트에 객체가 없을 때 CoreData는 쓸모없는 가져 오기 시도를해서는 안됩니다.
kpower

좋은 대답, 감사합니다! 이 메서드 이름은 정말 까다 롭습니다. 이 엉망이 모든 것을 최대 잘못된 하나에 쉽게
자칼

대단한 대답, 설명해 주셔서 감사합니다 . 오류를 발생시키려는 시도에서 예외가 발생하는 것을 방지하기 위해 먼저 objectWithId:전화 를 걸어야 할 필요성이 insertObject저에게 분명하지 않았습니다.
Stanislav Pankevich

3
objectRegisteredForID:다른 컨텍스트에있는 작업의 objectID 목록이 있고 로컬 컨텍스트에 오래된 데이터가있을 수있는 항목 만 업데이트하려는 경우에 유용합니다. 이렇게하면 개체 그래프 (및 메모리 사용량)를 확인하고 개체 ID를 반복 -registeredObjects하고 확인하여 컨텍스트에 대해 개체에 오류가 있는지 확인하는 것보다 낫습니다 .
Sterling Archer

4

objectWithID:찾고있는 방법이며이를 수행하는 데 권장되는 방법입니다. objectWithID:NSManagedObjectContext를 사용하여이 작업을 수행하는 다른 방법과 달리 필요한만큼만 개체를 ​​끌어옵니다. objectWithID:백업 저장소로 이동하기 전에 상위 컨텍스트, 영구 저장소 조정자 및 영구 저장소 자체에서 메모리 내 정보를 올바르게 사용합니다.

이는 WWDC 2012 세션 "핵심 데이터 모범 사례" 에서 자세히 다룹니다 .


당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.