Zoeken…


Opmerkingen

Dit is een implementatie van de Core Data Stack die in eerste instantie in het AppDelegate bestand wordt geplaatst als het project met Core Data wordt gemaakt wanneer het project wordt gemaakt. Deze functies kunnen ook worden geïmplementeerd in een afzonderlijke klasse voor CoreDataStack.swift . Een van de belangrijkste functies is het ophalen van NSManagedObjectContext.

Doelstelling C

- (NSManagedObjectContext *)managedObjectContext {...}

Swift 2

lazy var managedObjectContext: NSManagedObjectContext = {...}

Swift 3

lazy var persistentContainer: NSPersistentContainer = {...)
let managedObjectContext = persistentContainer.viewContext

De Core Data-stapel die communiceert tussen de objecten in uw applicatie en externe datastores. De Core Data-stack verwerkt alle interacties met de externe datastores zodat uw toepassing zich kan concentreren op de bedrijfslogica. De stapel bestaat uit drie primaire objecten: de beheerde objectcontext ( NSManagedObjectContext ), de persistente winkelcoördinator ( NSPersistentStoreCoordinator ) en het beheerde objectmodel ( NSManagedObjectModel ).

NSManagedObjectModel

De NSManagedObjectModel instantie beschrijft de gegevens waartoe de Core Data-stapel toegang heeft. NSManagedObjectModel (vaak de 'moeder' genoemd) wordt in het geheugen geladen als de eerste stap bij het maken van de stapel. Een voorbeeld van het NSManagedObjectModel is DataModel.momd. Het NSManagedObjectModel definieert de structuur van de gegevens

NSPersistentStoreCoordinator

De NSPersistentStoreCoordinator realiseert objecten uit de gegevens in de persistent store en geeft deze objecten door aan de aanvragende NSManagedObjectContext . Het maakt nieuwe exemplaren van de entiteiten in het model en haalt bestaande exemplaren op uit een persistent store ( NSPersistentStore ). De NSPersistentStoreCoordinator controleert ook of de gegevens een consistente status hebben die overeenkomt met de definities in het NSManagedObjectModel .

NSManagedObjectContext

Wanneer u objecten uit een blijvende winkel haalt, brengt u tijdelijke kopieën naar het kladblok waar ze een objectgrafiek vormen (of een verzameling objectgrafieken). U kunt deze objecten vervolgens wijzigen, tenzij u deze wijzigingen daadwerkelijk opslaat, maar de permanente opslag blijft ongewijzigd.

Alle beheerde objecten moeten worden geregistreerd met een beheerde objectcontext. U gebruikt de context om objecten aan de objectgrafiek toe te voegen en objecten uit de objectgrafiek te verwijderen. De context houdt de wijzigingen bij die u aanbrengt, zowel in de kenmerken van afzonderlijke objecten als in de relaties tussen objecten. Door wijzigingen bij te houden, kan de context u ongedaan maken en opnieuw ondersteunen. Het zorgt er ook voor dat als u relaties tussen objecten verandert, de integriteit van de objectgrafiek behouden blijft.

Wanneer u wijzigingen opslaat, zorgt de context ervoor dat uw objecten zich in een geldige status bevinden. De wijzigingen worden naar de permanente winkel (of winkels) geschreven, nieuwe records worden toegevoegd voor objecten die u hebt gemaakt en records zijn verwijderd voor objecten die u hebt verwijderd.

Bron: Apple Core Data Programming: de Core Data Stack initialiseren

Doelstelling-C-voorbeeld

Dit is een eenvoudige maar robuuste set-up van kerngegevens voor iOS 10+. Er zijn precies twee manieren om toegang te krijgen tot kerngegevens:

  1. viewContext . De viewContext kan alleen worden gebruikt vanuit de hoofdthread en alleen voor lezen.
  2. sterke enqueueCoreDataBlock . Al het schrijven moet gebeuren met enqueueCoreDataBlock . Het is niet nodig om op te slaan, het wordt automatisch opgeslagen. Alle schrijfbewerkingen worden in de wachtrij geplaatst zodat er nooit schrijfconflicten kunnen zijn.

Zorg ervoor dat u NOOIT managedObjects uit context in een andere context gebruikt. Gooi ook alle objecten weg die zijn gemaakt of opgehaald in enqueueCoreDataBlock omdat de context die ze ondersteunt wordt vernietigd nadat het blok is uitgevoerd.

// CoreDataManager.h

@interface CoreDataManager : NSObject
@property (nonatomic, readonly) NSManagedObjectContext * viewContext;
- (void)enqueueCoreDataBlock:(void (^)(NSManagedObjectContext* context))block;
@end

// CoreDataManager.m

@implementation NSManagedObjectContext(SaveIfNeeded)
-(BOOL) saveIfNeeded{
    BOOL toReturn = YES;
    if ([self hasChanges]) {
        NSError *error;
        toReturn = [self save:&error];
        if (toReturn == NO || error)
        {
            //Here you should log to your analytics service
            NSLog(@"--- Failed to commit data\n error: %@", error);
        }
    }
    return toReturn;
}
@end
@interface CoreDataManager ()
@property (nonatomic, strong) NSPersistentContainer* persistentContainer;
@property (nonatomic, strong) NSOperationQueue* persistentContainerQueue;    
@end
@implementation CoreDataManager

- (id)init
{
    self = [super init]
    if (self)
    {
        self.persistentContainer = [[NSPersistentContainer alloc] initWithName:@"PROJECT_NAME_ALSO_NAME_OF_MODEL" managedObjectModel:managedObjectModel];
        [self.persistentContainer loadPersistentStoresWithCompletionHandler:^(NSPersistentStoreDescription * description, NSError * error) {              
        }];
        self.persistentContainer.viewContext.automaticallyMergesChangesFromParent = YES;
        _persistentContainerQueue = [[NSOperationQueue alloc] init];
        _persistentContainerQueue.maxConcurrentOperationCount = 1;
        _persistentContainerQueue.name = @"persistentContainerQueue";
        dispatch_queue_t queue = dispatch_queue_create("persistentContainerQueue.dispatchQueue", DISPATCH_QUEUE_SERIAL);
        _persistentContainerQueue.underlyingQueue = queue;            
    }
}

- (void)enqueueCoreDataBlock:(void (^)(NSManagedObjectContext* context))block{
    void (^blockCopy)(NSManagedObjectContext*) = [block copy];

    [self.persistentContainerQueue addOperation:[NSBlockOperation blockOperationWithBlock:^{
        NSManagedObjectContext* context =  self.persistentContainer.newBackgroundContext;
        [context performBlockAndWait:^{
            blockCopy(context);
            [context saveIfNeeded];
        }];
    }]];
}

-(NSManagedObjectContext*) viewContext{
    if (![NSThread mainThread]) {
        //here you should log to you analytics service. If you are in developer mode you should crash to force you to fix this
        NSLog(@"access context on wrong thread!!");
    }
    return self.persistentContainer.viewContext;
}

Swift 2-voorbeeld

// Core Data stack

lazy var applicationDocumentsDirectory: NSURL = {
    let urls = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask)
    return urls[urls.count-1]
}()

lazy var managedObjectModel: NSManagedObjectModel = {
    let modelURL = NSBundle.mainBundle().URLForResource("ProjectName", withExtension: "momd")!
    return NSManagedObjectModel(contentsOfURL: modelURL)!
}()

lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator = {

    let coordinator = NSPersistentStoreCoordinator(managedObjectModel: self.managedObjectModel)
    let url = self.applicationDocumentsDirectory.URLByAppendingPathComponent("SingleViewCoreData.sqlite")
    var failureReason = "There was an error creating or loading the application's saved data."
    do {
        try coordinator.addPersistentStoreWithType(NSSQLiteStoreType, configuration: nil, URL: url, options: nil)
    } catch {
        var dict = [String: AnyObject]()
        dict[NSLocalizedDescriptionKey] = "Failed to initialize the application's saved data"
        dict[NSLocalizedFailureReasonErrorKey] = failureReason

        dict[NSUnderlyingErrorKey] = error as NSError
        let wrappedError = NSError(domain: "YOUR_ERROR_DOMAIN", code: 9999, userInfo: dict)
        print("Unresolved error \(wrappedError), \(wrappedError.userInfo)")
        abort()
    }
    
    return coordinator
}()

lazy var managedObjectContext: NSManagedObjectContext = {
    let coordinator = self.persistentStoreCoordinator
    var managedObjectContext = NSManagedObjectContext(concurrencyType: .MainQueueConcurrencyType)
    managedObjectContext.persistentStoreCoordinator = coordinator
    return managedObjectContext
}()

// Core Data Saving support

func saveContext () {
    if managedObjectContext.hasChanges {
        do {
            try managedObjectContext.save()
        } catch {
            let nserror = error as NSError
            print("Unresolved error \(nserror), \(nserror.userInfo)")
            abort()
        }
    }
}

iOS 10-voorbeeld in Swift

lazy var persistentContainer: NSPersistentContainer = {
    
    let container = NSPersistentContainer(name: "ProjectName")
    container.loadPersistentStores(completionHandler: { (storeDescription, error) in
        
        if let error = error {
            fatalError("Unresolved error \(error), \(error.userInfo)")
        }
    })
    return container
}()
    
func saveContext () {
    let context = persistentContainer.viewContext
    
    do {
        try context.save()
    } catch {
        let nserror = error as NSError
        fatalError("Unresolved error \(nserror), \(nserror.userInfo)")
    }
    
    if context.hasChanges {
        print("changes occured")
    }else {
        print("no changes occured")
    }
    
}


Modified text is an extract of the original Stack Overflow Documentation
Licentie onder CC BY-SA 3.0
Niet aangesloten bij Stack Overflow