我有一个tableviewcontroller,它显示Core Data模型的对象。我的导航栏中有一个按钮,单击它时会删除模型中的行和对象。出于测试目的,在AppDelegate中,我将具有2个属性的对象添加到仅模型实体。然后我在tableview中显示这个对象。在删除按钮上单击所选行已删除,我已将其设置为从数据模型中删除对象,但它不会保存更改。每次重建和运行应用程序时,都会添加更多内容,而当我删除它们时,更改将一直持续到下一次重建。如何在我的代码中修复此问题?
AppDelegate.h
#import <UIKit/UIKit.h>
#import "favTable.h"
@interface AppDelegate : UIResponder <UIApplicationDelegate> {
NSManagedObjectContext *managedObjectContext;
NSManagedObject *favoritesInfo;
}
@property (strong, nonatomic) UIWindow *window;
@property (strong, nonatomic) favTable *viewController;
@property (strong, nonatomic) UINavigationController *navController;
@property (nonatomic, retain) NSManagedObject *favoritesInfo;
@property (nonatomic, retain, readonly) NSManagedObjectModel *managedObjectModel;
@property (nonatomic, retain) NSManagedObjectContext *managedObjectContext;
@property (nonatomic, retain, readonly) NSPersistentStoreCoordinator *persistentStoreCoordinator;
- (void)saveContext;
- (NSURL *)applicationDocumentsDirectory; // reference files for core data
@end
AppDelegate.m
#import "AppDelegate.h"
@implementation AppDelegate
@synthesize window = _window;
@synthesize viewController = _viewController;
@synthesize navController = _navController;
@synthesize managedObjectContext = _managedObjectContext;
@synthesize managedObjectModel = _managedObjectModel;
@synthesize persistentStoreCoordinator = _persistentStoreCoordinator;
@synthesize favoritesInfo;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
NSManagedObjectContext *context = [self managedObjectContext];
favoritesInfo = [NSEntityDescription
insertNewObjectForEntityForName:@"FavoritesInfo"
inManagedObjectContext:context];
[favoritesInfo setValue:@"Product 1" forKey:@"name"];
[favoritesInfo setValue:[NSNumber numberWithInt:15] forKey:@"score"];
NSError *error;
if (![context save:&error]) {
NSLog(@"Whoops, couldn't save: %@", [error localizedDescription]);
}
return YES;
}
// Core Data methods
- (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:@"DataModel" withExtension:@"momd"];
_managedObjectModel = [[NSManagedObjectModel alloc] initWithContentsOfURL:modelURL];
return _managedObjectModel;
}
- (NSPersistentStoreCoordinator *)persistentStoreCoordinator
{
if (_persistentStoreCoordinator != nil) {
return _persistentStoreCoordinator;
}
NSURL *storeURL = [[self applicationDocumentsDirectory] URLByAppendingPathComponent:@"DataModel.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];
}
@end
favtable.h
#import <UIKit/UIKit.h>
@interface favTable : UITableViewController <NSFetchedResultsControllerDelegate>
{
NSFetchedResultsController *fetchedResultsController;
NSManagedObjectContext *managedObjectContext;
NSArray *favArr;
NSMutableArray *favName;
}
@property (nonatomic, retain) NSArray *favArr;
@property (strong, nonatomic) ScannedProductControllerViewController *spVC;
@property (nonatomic, retain) NSManagedObjectContext *managedObjectContext;
@property (nonatomic, strong) NSMutableArray *favName;
@property (nonatomic, retain) NSFetchedResultsController *fetchedResultsController;
@property (strong, nonatomic) ecoViewController *mainController;
@end
favtable.m
#import "favTable.h"
#import "AppDelegate.h"
@interface favTable ()
@end
@implementation favTable
@synthesize favArr;
@synthesize managedObjectContext;
@synthesize fetchedResultsController;
@synthesize favName;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.title = @"Favorites";
self.navigationController.navigationBar.translucent = NO;
UIBarButtonItem *delButton = [[UIBarButtonItem alloc]
initWithTitle:@"Del"
style: UIBarButtonItemStyleBordered
target: self
action:@selector(delItemToArray)];
self.navigationItem.rightBarButtonItem = delButton;
// passing the array of addedtofavorites to the total one with all favorites
self.managedObjectContext = ((AppDelegate *) [UIApplication sharedApplication].delegate).managedObjectContext;
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription
entityForName:@"FavoritesInfo" inManagedObjectContext:managedObjectContext];
[fetchRequest setEntity:entity];
fetchRequest.resultType = NSDictionaryResultType;
[fetchRequest setPropertiesToFetch:[NSArray arrayWithObjects:@"name", nil]];
NSError *error=nil;
self.favArr=[[self.managedObjectContext executeFetchRequest:fetchRequest error:&error] mutableCopy];
if (error!=nil) {
NSLog(@" fetchError=%@,details=%@",error,error.userInfo);
}
self.favName = self.favName = [[self.favArr valueForKey:@"name"]mutableCopy];
}
- (void)viewDidUnload
{
[super viewDidUnload];
// Release any retained subviews of the main view.
// e.g. self.myOutlet = nil;
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
#warning Potentially incomplete method implementation.
// Return the number of sections.
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
#warning Incomplete method implementation.
// Return the number of rows in the section.
return [favName count];;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Cell";
UITableViewCell *cell;
// Configure the cell...
cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
// Configure the cell... setting the text of our cell's label
cell.textLabel.text = [favName objectAtIndex:indexPath.row];
return cell;
}
//Delete Item To Array
- (void)delItemToArray {
AppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
NSManagedObjectContext *context = [appDelegate managedObjectContext];
AppDelegate *appDelegatee = (AppDelegate *)[[UIApplication sharedApplication] delegate];
[context deleteObject:appDelegatee.favoritesInfo];
NSIndexPath *indexPath;
[favName removeObjectAtIndex:indexPath.row];
[appDelegatee saveContext]; // to save changes
NSError *error = nil;
if (![context save:&error])
{
NSLog(@"Error deleting movie, %@", [error userInfo]);
}
[self.tableView reloadData];
}
答案 0 :(得分:-1)
您的代码存在很多问题,我不知道从哪里开始。
班级名称应以大写字母开头
您在FavTable.m中为同一个app delegate singleton使用了两个变量
您正在声明变量indexPath
而未初始化它
应该在NSFetchedResultsControllerDelegate方法中处理表视图的重新加载。
您显然没有使用获取的结果控制器。为什么?
你的可变数组favName
有一个令人困惑的名字,导致普遍缺乏可读性
你写了self.favName = self.favName
......的达达主义语句
您的按钮处理程序方法名称delItemToArray
同样具有冒险精神
favArr
是一个不可变数组,但是你为它分配了一个可变数组
favName
和favArr
是多余的,因为favArr
已包含所有信息
您在删除期间修改favName
但未对数据更改做出反应。
应用代表没有业务保留对favoritesInfo
的引用
等......等等......
简而言之,你就是这样。在处理Objective-C和核心数据之前,您应该投入一些时间来获取一些基本的编程技能。