Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/objective-c/25.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Iphone 具有多个通道的标准核心数据迁移不起作用_Iphone_Objective C_Ios_Core Data_Core Data Migration - Fatal编程技术网

Iphone 具有多个通道的标准核心数据迁移不起作用

Iphone 具有多个通道的标准核心数据迁移不起作用,iphone,objective-c,ios,core-data,core-data-migration,Iphone,Objective C,Ios,Core Data,Core Data Migration,我在这里学习了有关核心数据标准迁移的教程: 然后是一个关于多次传球的例子: 这给了我这里的结果代码: - (NSManagedObjectContext *)managedObjectContext { if (managedObjectContext != nil) { return managedObjectContext; } NSPersistentStoreCoordinator *coordinator = [self persiste

我在这里学习了有关核心数据标准迁移的教程:

然后是一个关于多次传球的例子:

这给了我这里的结果代码:

- (NSManagedObjectContext *)managedObjectContext {

    if (managedObjectContext != nil) {
        return managedObjectContext;
    }

    NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator];
    if (coordinator != nil) {
        managedObjectContext = [TICDSSynchronizedManagedObjectContext new];
        [managedObjectContext setPersistentStoreCoordinator: coordinator];
    }
    return managedObjectContext;
}
- (NSManagedObjectModel *)managedObjectModel {

    if (managedObjectModel != nil) {
        return managedObjectModel;
    }

    //    managedObjectModel = [[NSManagedObjectModel mergedModelFromBundles:nil] retain];
    NSString *modelPath = [[NSBundle mainBundle] pathForResource:@"EntryDatabase" ofType:@"momd"];
    NSURL *modelURL = [NSURL fileURLWithPath:modelPath];
    managedObjectModel = [[NSManagedObjectModel alloc] initWithContentsOfURL:modelURL];

    return managedObjectModel;
}
- (NSPersistentStoreCoordinator *)persistentStoreCoordinator {

    if (persistentStoreCoordinator != nil) {
        return persistentStoreCoordinator;
    }

    NSString *storePath = [[self applicationDocumentsDirectory]
                           stringByAppendingPathComponent:@"CoreDataStore.sqlite"];

    NSFileManager *fileManager = [NSFileManager defaultManager];
    // If the expected store doesn't exist, copy the default store.
    NSLog(@"file exists at path: %@, %i", storePath, [fileManager fileExistsAtPath:storePath]);
    if (![fileManager fileExistsAtPath:storePath]) {
        NSString *defaultStorePath = [[NSBundle mainBundle] pathForResource:@"CoreDataStore" ofType:@"sqlite"];
        if (defaultStorePath) {
            [fileManager copyItemAtPath:defaultStorePath toPath:storePath error:NULL];
        }
    }

    persistentStoreCoordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:[self managedObjectModel]];

    NSURL *storeUrl = [NSURL fileURLWithPath:storePath];
    NSError *error;
    NSDictionary *pscOptions = [NSDictionary dictionaryWithObjectsAndKeys:
                                [NSNumber numberWithBool:YES], NSMigratePersistentStoresAutomaticallyOption,
                                [NSNumber numberWithBool:NO], NSInferMappingModelAutomaticallyOption,
                                nil];

    if (![persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType
                                                  configuration:nil
                                                            URL:storeUrl
                                                        options:pscOptions
                                                          error:&error]) {
        NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
    }

    return persistentStoreCoordinator;
}

- (BOOL)checkForMigration
{
    BOOL migrationSuccess = NO;
    NSString *storeSourcePath = [[self applicationDocumentsDirectory]
                                 stringByAppendingPathComponent:@"CoreDataStoreNew.sqlite"];
    NSFileManager *fileManager = [NSFileManager defaultManager];

    if (![fileManager fileExistsAtPath:storeSourcePath]) {
        //Version 2 SQL has not been created yet, so the source is still version 1...
        storeSourcePath = [[self applicationDocumentsDirectory]
                           stringByAppendingPathComponent:@"CoreDataStore.sqlite"];
    }

    NSURL *storeSourceUrl = [NSURL fileURLWithPath: storeSourcePath];
    NSError *error = nil;
    NSDictionary *sourceMetadata = [NSPersistentStoreCoordinator
                                    metadataForPersistentStoreOfType:NSSQLiteStoreType
                                    URL:storeSourceUrl
                                    error:&error];
    if (sourceMetadata) {
        NSString *configuration = nil;
        NSManagedObjectModel *destinationModel = [self.persistentStoreCoordinator managedObjectModel];

        //Our Source 1 is going to be incompatible with the Version 2 Model, our Source 2 won't be...
        BOOL pscCompatible = [destinationModel isConfiguration:configuration compatibleWithStoreMetadata:sourceMetadata];
        NSLog(@"Is the STORE data COMPATIBLE? %@", (pscCompatible==YES) ?@"YES" :@"NO");

        if (pscCompatible == NO) {
            migrationSuccess = [self performMigrationWithSourceMetadata:sourceMetadata toDestinationModel:destinationModel];
        }
    }
    else {
        NSLog(@"checkForMigration FAIL - No Source Metadata! \nERROR: %@", [error localizedDescription]);
    }
    return migrationSuccess;
}


- (BOOL)performMigrationWithSourceMetadata :(NSDictionary *)sourceMetadata
                         toDestinationModel:(NSManagedObjectModel *)destinationModel
{


    BOOL migrationSuccess = NO;
    //Initialise a Migration Manager...
    NSManagedObjectModel *sourceModel = [NSManagedObjectModel mergedModelFromBundles:nil
                                                                    forStoreMetadata:sourceMetadata];
    //Perform the migration...
    if (sourceModel) {
        NSMigrationManager *standardMigrationManager = [[NSMigrationManager alloc]
                                                        initWithSourceModel:sourceModel
                                                        destinationModel:destinationModel];

        NSArray *mappingModelNames = [NSArray arrayWithObjects:@"StepOne", @"StepTwo", nil];
        NSDictionary *sourceStoreOptions = nil;

        NSString *destinationStorePath = [[self applicationDocumentsDirectory]
                                          stringByAppendingPathComponent:@"CoreDataStoreNew.sqlite"];

        NSURL *destinationStoreURL = [NSURL fileURLWithPath: destinationStorePath];

        NSString *destinationStoreType = NSSQLiteStoreType;

        NSDictionary *destinationStoreOptions = nil;

        for (NSString *mappingModelName in mappingModelNames) {

            NSError *error;

            NSURL *fileURL = [[NSBundle mainBundle] URLForResource:mappingModelName withExtension:@"cdm"];

            NSMappingModel *mappingModel = [[NSMappingModel alloc] initWithContentsOfURL:fileURL];

            migrationSuccess = [standardMigrationManager migrateStoreFromURL:destinationStoreURL
                                                                        type:NSSQLiteStoreType
                                                                     options:sourceStoreOptions
                                                            withMappingModel:mappingModel
                                                            toDestinationURL:destinationStoreURL
                                                             destinationType:destinationStoreType
                                                          destinationOptions:destinationStoreOptions
                                                                       error:&error];

            NSLog(@"Error: %@", error);
        }

    }

    return migrationSuccess;

}
但是,应用程序内存不足,并在
persistentStoreCoordinator
中的一行崩溃:

if (![persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType
                                              configuration:nil
                                                        URL:storeUrl
                                                    options:pscOptions
                                                      error:&error]) {

我记得我也遵循了这个教程

事实上,我发现这样做是不对的。顺便问一下,您是否阅读了关于该教程的最后一条评论,并尝试删除提到的行?也许这能解决你的问题

无论如何,在我的例子中,我意识到(在遵循本教程之后,修改没有帮助)有一种更简单的方法


在你的情况下,我不知道,但是,如果这个小修改不能解决它,我真的会寻找另一个参考-因为这真的不是正确的方法,并导致你在错误的方向上,因为它试图自己做所有事情,而不是像我发现的那样使用苹果核心数据迁移过程背后的逻辑。

几年前我解决的问题是从一个存储库中取出一个子树,然后复制到另一个存储库中,我所做的应该对你有用。我是在Mac上这样做的,所以内存不是问题,但是根据核心数据编程指南“减少内存开销”,通过适当的故障处理和减少内存,您应该能够让它正常工作

下面的解决方案基于这样一个假设,即MOM没有那么大的不同。让我介绍“A”一词用于现有上下文,而“B”一词用于新上下文

1) 第一步是在B中复制A中的每个对象。如果类保持不变,则可以。这意味着对于每个对象,都需要一个包含实体中所有值的列表。我建议使用键——每个实体类型的属性键数组,这将使编码更容易(如果可以的话)。否则,你实际上可以从妈妈那里得到钥匙——这就是我在旧代码中所做的

现在关键的一步是——你必须创建一个翻译词典(也许你需要两个——我已经创建了),对于a中的每个实体,你都知道“B”中对应的那个。您可以使用'objectID'属性(但对于B,在保存此值更改后,在完成之前不要进行保存)

2) 现在您已经完全重新创建了所有实体,您需要将它们“连接”起来,以便正确设置所有关系。同样,为每个实体类型创建一些键数组,然后在循环中查看“a”中的每个关系,获取它指向的实体,使用转换表在“B”中找到相应的一个,并在“B”中设置值

瞧!完成了。很明显,你做的是添加还是删除?你做上述操作是为了反映A-B中的更改


同样,我也不需要太担心Mac上的内存,所以也不需要技巧来降低内存。我相信使用faulting('refreshObject:mergeChanges:')会对您有所帮助,但您也不必这样做(即便如此,可能只是对象太大了)。

您刚才不是也发过同样的问题吗?如果不是的话,其他一些人发布了几乎完全相同的东西。我现在确实有了一个想法,因为我没有earler,因为我使用了一种在这里也应该有效的技术(但它不是微不足道的),将在文本编辑器中编写,然后稍后添加。@DavidH我已经就同一代码问了其他问题。期待看到你的替代品。你删除了那些线路了吗。你发现了哪种替代方案?事实证明,我的案例非常简单-因此我所要做的就是使用添加了所有新属性和关系的正常迁移-我不确定它是否适用于你。抱歉,但我能给出的唯一建议是重新检查您的新数据模型,看看您是否真的需要更复杂的转换…-在我的情况下(在我了解了leightweight可以做什么之后),这就是我所需要的