【发布时间】:2011-10-12 21:32:55
【问题描述】:
我在没有 Core Data 的情况下开始了这个项目,现在我想将该功能添加到我的应用程序中。我该怎么做呢?
当您在创建新项目时实际勾选使用核心数据时,XCode 会设置哪些额外的东西?
【问题讨论】:
标签: iphone objective-c ipad core-data
我在没有 Core Data 的情况下开始了这个项目,现在我想将该功能添加到我的应用程序中。我该怎么做呢?
当您在创建新项目时实际勾选使用核心数据时,XCode 会设置哪些额外的东西?
【问题讨论】:
标签: iphone objective-c ipad core-data
一个技巧是只创建一个支持 Core Data 的新空项目。这将为您提供必要的代码,您可以将其复制到原始项目并进行编译。
唯一的问题是您需要处理 Core Data 头文件。 Xcode 在使用模板生成文件时将其放入预编译的头文件中。因此,您可以将以下行添加到您的 .pch 文件中:
#import <CoreData/CoreData.h>
或者您可以将其添加到需要的 .m 文件中。
它就像一个魅力。请注意下面 Luka 关于如何在 Xcode5 中执行此操作的评论。
【讨论】:
只是为了阐述将 Core Data 添加到以前没有的项目中实际需要执行的所有步骤:
点击您的应用程序目标(在左侧窗格中,其顶部图标带有您的应用程序名称),然后转到“构建阶段”选项卡,然后在“将二进制文件与库链接”上,单击小“+”在底部然后找到'CoreData.framework'并将其添加到您的项目中
然后使用以下方法在所有需要它的对象上导入 coredata(非性感方式):
#import <CoreData/CoreData.h>
或在您的 .pch 文件中的常见导入下方添加导入(更性感),如下所示:
#ifdef __OBJC__
#import <UIKit/UIKit.h>
#import <Foundation/Foundation.h>
#import <CoreData/CoreData.h>
#endif
要添加 .xcdatamodel 文件,请在右侧窗格中右键单击/控制单击您的文件(例如在资源文件夹中以确保安全)并选择添加新文件,在选择文件类型时单击核心数据选项卡然后单击“数据模型”,为其命名并单击下一步和完成,它将将其添加到您的项目中。当您单击此模型对象时,您将看到将实体添加到您的项目中的界面以及您想要的任何关系。
将这些对象添加到 AppDelegate.h
@property (nonatomic, retain, readonly) NSManagedObjectModel *managedObjectModel;
@property (nonatomic, retain, readonly) NSManagedObjectContext *managedObjectContext;
@property (nonatomic, retain, readonly) NSPersistentStoreCoordinator *persistentStoreCoordinator;
- (NSURL *)applicationDocumentsDirectory; // nice to have to reference files for core data
像这样在 AppDelegate.m 中合成之前的对象:
@synthesize managedObjectContext = _managedObjectContext;
@synthesize managedObjectModel = _managedObjectModel;
@synthesize persistentStoreCoordinator = _persistentStoreCoordinator;
然后将这些方法添加到 AppDelegate.m(确保将您添加的模型的名称放在显示的位置):
- (void)saveContext{
NSError *error = nil;
NSManagedObjectContext *managedObjectContext = self.managedObjectContext;
if (managedObjectContext != nil) {
if ([managedObjectContext hasChanges] && ![managedObjectContext save:&error]) {
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
}
}
- (NSManagedObjectContext *)managedObjectContext{
if (_managedObjectContext != nil) {
return _managedObjectContext;
}
NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator];
if (coordinator != nil) {
_managedObjectContext = [[NSManagedObjectContext alloc] init];
[_managedObjectContext setPersistentStoreCoordinator:coordinator];
}
return _managedObjectContext;
}
- (NSManagedObjectModel *)managedObjectModel{
if (_managedObjectModel != nil) {
return _managedObjectModel;
}
NSURL *modelURL = [[NSBundle mainBundle] URLForResource:@"NAMEOFYOURMODELHERE" withExtension:@"momd"];
_managedObjectModel = [[NSManagedObjectModel alloc] initWithContentsOfURL:modelURL];
return _managedObjectModel;
}
- (NSPersistentStoreCoordinator *)persistentStoreCoordinator
{
if (_persistentStoreCoordinator != nil) {
return _persistentStoreCoordinator;
}
NSURL *storeURL = [[self applicationDocumentsDirectory] URLByAppendingPathComponent:@"NAMEOFYOURMODELHERE.sqlite"];
NSError *error = nil;
_persistentStoreCoordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:[self managedObjectModel]];
if (![_persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL options:nil error:&error]) {
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
return _persistentStoreCoordinator;
}
#pragma mark - Application's Documents directory
// Returns the URL to the application's Documents directory.
- (NSURL *)applicationDocumentsDirectory{
return [[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject];
}
在 ViewController.h 中
@property (nonatomic, retain) NSManagedObjectContext *managedObjectContext;
在 ViewController.m 中
@synthesize managedObjectContext = _managedObjectContext;
在 AppDelegate 或创建 ViewController 的类中,将 managedObjectContext 设置为与 AppDelegate 相同
ViewController.managedObjectContext = self.managedObjectContext;
如果您希望使用 Core Data 的视图控制器成为 FetchedResultsController,那么您需要确保这些内容在您的 ViewController.h 中
@interface ViewController : UIViewController <NSFetchedResultsControllerDelegate> {
NSFetchedResultsController *fetchedResultsController;
NSManagedObjectContext *managedObjectContext;
}
@property (nonatomic, retain) NSFetchedResultsController *fetchedResultsController;
这是在 ViewController.m 中
@synthesize fetchedResultsController, managedObjectContext;
在所有这些之后,您现在可以使用这个 managedObjectContext 来运行 CoreData 所需的所有常用 fetchRequest!享受
【讨论】:
- (NSString *)applicationDocumentsDirectory; 应该是 - (NSURL *)applicationDocumentsDirectory;。否则它将与- (NSPersistentStoreCoordinator *)persistentStoreCoordinator 中的代码不匹配。我已经用更新的代码编辑了答案。
如果您想将 CoreData.framework 添加到您的项目中,请双击您的 Groups and Files 列表中的 Target。转到摘要窗格,然后单击链接库的“+”。选择 CoreData.framework。然后它将与您的项目链接。
【讨论】:
Xcode 将一堆东西添加到 Core Data 的标准模板中。
如果您不熟悉它,那么创建一个新的 Core Data 项目并将您自己的东西放入其中,而不是尝试将基础架构添加到您现有的项目中。
基本上你得到的是......
【讨论】:
通过将 Core Data 与新项目(包括)进行比较,将 Core Data 添加到您的项目中非常简单。核心数据。您需要在 AppDelegate 中添加一个“数据模型”文件和一些方法和 ivars。
查看实现文件中的Core Data Project Template -> “Core Data stack”。
【讨论】:
我发现最简单的方法是创建一个带有核心数据的新项目,删除项目中的文件并从非核心数据项目拖放到核心数据项目。 (Main.storyboard、AppDelegate、ViewController 等)
【讨论】: