【问题标题】:Programmatically Update an attribute in Core Data以编程方式更新 Core Data 中的属性
【发布时间】:2010-09-30 17:09:33
【问题描述】:

我查看了 Core Data 的所有类文档,但找不到以编程方式更新核心数据实体中的值的方法。比如我有一个类似这样的结构:

 id  | title
============
  1  | Foo  
  2  | Bar  
  3  | FooFoo

假设我想将 Bar 更新为 BarBar,我在任何文档中都找不到任何方法。

【问题讨论】:

    标签: objective-c cocoa core-data object


    【解决方案1】:
    NSManagedObject *object = [self.fetchedResultsController objectAtIndexPath:indexPath];
    
    NSManagedObjectContext *context = [self.fetchedResultsController managedObjectContext];
    
            NSArray *temp = [[NSArray alloc]initWithObjects:@"NewWord", nil];
    
    
            [object setValue:[temp objectAtIndex:0] forKey:@"title"];
    
    
    
            // Save the context.
            NSError *error = nil;
            if (![context save:&error]) {
                NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
                abort();
            }
    

    我认为这段代码会给你这个想法;)

    【讨论】:

      【解决方案2】:

      在 Core Data 中,对象就是对象——数据库不是你向其抛出命令的东西。

      要更新持久化的内容,请将其重新创建为对象、更新并保存。

      NSError *error = nil;
      
      //This is your NSManagedObject subclass
      Books * aBook = nil;
      
      //Set up to get the thing you want to update
      NSFetchRequest * request = [[NSFetchRequest alloc] init];
      [request setEntity:[NSEntityDescription entityForName:@"MyLibrary" inManagedObjectContext:context]];
      [request setPredicate:[NSPredicate predicateWithFormat:@"Title=%@",@"Bar"]];
      
      //Ask for it
      aBook = [[context executeFetchRequest:request error:&error] lastObject];
      [request release];
      
      if (error) {
      //Handle any errors
      }
      
      if (!aBook) {
          //Nothing there to update
      }
      
      //Update the object
      aBook.Title = @"BarBar";
      
      //Save it
      error = nil;
      if (![context save:&error]) {
                 //Handle any error with the saving of the context
      }
      

      【讨论】:

      • Core Data 是否自动保存?如果你想强制保存,你可以调用它,但它应该自动保存 AFAIK。
      • 并非如此。如果你让 XCode 在最近的版本中设置一个 Core Data 项目,模板代码会在“最后机会”的地方包含一些对托管对象上下文的保存方法的调用,例如应用程序委托中的 applicationWillTerminate,但这可能不太健壮比大多数应用程序需要的。保存调用很昂贵 - 为了完整起见,在进行非常小的更改之后的示例。
      【解决方案3】:

      如果我正确理解了您的问题,我认为您需要记住的只是托管对象与任何其他 Cocoa 类没有什么不同。属性有访问器和修改器,你可以在代码中使用,通过键值编码或绑定,只有在这种情况下它们是由 Core Data 生成的。唯一的技巧是,如果您想避免使用 setValue:ForKey:,您需要在类文件(如果有的话)中为您的实体手动声明生成的访问器。文档对此进行了更详细的描述,但简短的回答是您可以在数据模型设计器中选择您的属性,然后从“设计”菜单中选择复制 Obj-C 2.0 方法声明

      【讨论】:

        【解决方案4】:

        听起来您是在考虑底层关系数据库。 Core Data 的 API 是围绕模型对象构建的,而不是关系数据库。

        实体是一个 Cocoa 对象——NSManagedObject 的一个实例或它的某个子类。实体的属性是对象的属性。您可以使用键值编码,或者,如果您实现子类,则使用点语法或访问器方法来设置这些属性。

        Evan DiBiase 的回答显示了一种设置属性的正确方法——特别是访问器消息。这是点语法:

        bookTwo.title = @"BarBar";
        

        还有 KVC(您可以与普通的旧 NSManagedObject 一起使用):

        [bookTwo setValue:@"BarBar" forKey:@"title"];
        

        【讨论】:

          【解决方案5】:

          Apple documentation on using managed objects in Core Data 可能有你的答案。不过,简而言之,您应该能够执行以下操作:

          NSError *saveError;
          [bookTwo setTitle:@"BarBar"];
          if (![managedObjectContext save:&saveError]) {
              NSLog(@"Saving changes to book book two failed: %@", saveError);
          } else {
              // The changes to bookTwo have been persisted.
          }
          

          (注意:bookTwo 必须是与 managedObjectContext 关联的托管对象,此示例才能正常工作。)

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2017-02-27
            • 1970-01-01
            • 1970-01-01
            • 2017-01-22
            • 1970-01-01
            相关资源
            最近更新 更多