我是Core Data noob,正在开发我的第一个iOS应用程序。经过多次Stack Overflowing我正在使用这段代码:
NSString *path = [[NSBundle mainBundle] pathForResource:@"CoreData" ofType:@"momd"];
if (!path) {
path = [[NSBundle mainBundle] pathForResource:@"CoreData" ofType:@"mom"];
}
NSAssert(path != nil, @"Unable to find Resource in main bundle");
CoreData是我的应用程序的名称。
我试图通过在我的iPhone模拟器中找到sqlite文件的路径,然后进入并插入该sqlite文件,将初始数据放入应用程序。但在某些时候,我移动了sqlite(认为它会创建一个新副本),从模拟器中删除应用程序,sqlite文件消失了。我不确定我是否遗漏了这个过程的某些部分(这是几个小时前),但最终结果是一切都搞砸了。
如何重新定位此sqlite / momd文件? “清洁”和“清理所有目标”都显示为灰色。
我很高兴发布我的应用程序中的相关代码,这有助于解释这个问题,但是有大量与Core Data相关的代码,我不明白,所以我不确定发布哪个部分!非常感谢任何帮助。
答案 0 :(得分:44)
以下是一些建议:
您发布的用于获取.mom(d)
文件的代码并不完全是推荐的方式。请改用mergedModelFromBundles
,如
self.managedObjectContent= [NSManagedObjectModel mergedModelFromBundles:nil];
它负责获取路径,选择/合并正确的mom
或momd
,以及一步完成MOC的初始化。你应该使用它。但请注意,您需要暂时清理构建过程,如this SO question/answer中所述。
这表明,尽管通过StackOverflow进行爬行通常很好,但在处理像CoreData这样的大型框架时,这并不是最好的方法。
老实说,花一天时间从头到尾阅读the documentation。您可能想要谷歌代码并立即开始编码,但从长远来看,阅读文档肯定会大大节省开发时间。
另外,Marcus Zarra的CoreData一书(见here)给了我很多帮助。它可能看起来很昂贵,但它完全值得。
在另一个主题上,我认为将预先煮熟的sqlite文件放入模拟器的目录(~/Library/Application Support/iPhone Simulator/
内)并不是一个好的策略,即使是出于开发目的......因为它没有在真实设备上工作。如果您需要这样做,请将sqlite文件作为应用程序的资源,并在启动时将其复制到Documents
或Caches
,然后再使用它。
答案 1 :(得分:18)
如果清洁目标菜单项是灰色的,则可能是您正在运行该应用程序。
您获取mom / momd路径的方式看起来就像您尝试在事后整合CoreData(而不是在创建项目时选择包含它)。我遇到了和你一样的问题。查找momd的默认代码假定它存在,并且如果您将数据模型的版本添加到项目中,您也应该能够。
为此,请选择xcdatamodel文件,然后在“设计”菜单中选择“数据模型”>添加模型版本。然后,您将拥有CoreData.xcdatamodeld,其子树包含Coredata.xcdatamodel和新版本。您可以删除额外的版本,您将拥有所需的层次结构。如果你构建并查看App包,你会看到里面有妈妈的CoreData.momd目录。
到目前为止,我发现的任何CoreData教程都没有包含这些步骤。我希望它有用!
答案 2 :(得分:6)
实际答案: 如果您遇到路径问题,可以尝试以下代码。您还需要检查您的xcdatamodel文件是否包含在目标资源中。
[[NSBundle bundleForClass:[self class]] pathForResource:@"CoreData" ofType:@"momd"]
更好的答案:代表NSManagedObjectModel的momd文件和NSPersistentStore对象使用的sqlite文件之间存在区别。使用CoreData的最佳方法是让SDK处理与sqlite的所有交互。关于sqlite,你唯一需要设置的就是告诉你的NSPersistantStore存放你的sqlite文件的位置。您在托管对象模型中定义的托管对象将为您处理所有数据插入和更新。
如果您不熟悉我引用的对象,请查看Apple文档以获得非常有用的概述。您肯定希望花时间去掌握完整的CoreData堆栈,因为如果您按照Apple期望的方式使用Core Data,时间投资将获得更少的麻烦。这是一个比许多Web开发人员习惯的抽象设计更抽象的设计,但是试图通过直接使用SQLite来规避抽象,会产生一系列复杂性。
答案 3 :(得分:4)
我发现在模拟器“磁盘映像”中查看我的可执行文件非常有价值。
如果您进入〜/ Library / Application Support / iPhone Simulator // Applications,您可以在手机上看到应用程序。找出哪一个是你的(使用find,或查看日期),然后浏览到你的target.app并查找.momd文件。
在我的情况下,我的妈妈的名字与我的.xcdatamodeld文件名不同,这就是为什么核心数据无法加载它。一旦我更正了AppDelegate中的名称,事情就开始正常工作了。
请注意,妈妈“文件”似乎实际上是一个目录(如.app设置)。
-
在添加代码以初始化核心数据方面;我也是这样做的。我创建了一个新的空白项目,启用了核心数据,并复制了AppDelegate文件中核心数据的所有初始化步骤。有很多与初始化整个堆栈相关的东西,所以如果不存在,你需要把它放在那里。
答案 4 :(得分:1)
如果您在模型中添加了版本,请将.mom更改为.momd
NSString *path = [[NSBundle mainBundle] pathForResource:@"CoreData" ofType:@"momd"];
if (!path) {
path = [[NSBundle mainBundle] pathForResource:@"CoreData" ofType:@"momd"];