从 Coredata 中删除一个对象(出现错误)

Posted

技术标签:

【中文标题】从 Coredata 中删除一个对象(出现错误)【英文标题】:delete an object from Coredata (getting an error) 【发布时间】:2015-07-12 12:56:14 【问题描述】:

我尝试从 coredata 中删除与 Test2 匹配的对象。我试过这个:

    let context = self.fetchedResultsController.managedObjectContext
    let fetchRequest = NSFetchRequest(entityName:"Person")
    fetchRequest.predicate = NSPredicate(format: "name = Test2")
    var error : NSError?
    let results = managedObjectContext!.executeFetchRequest(fetchRequest, error:&error)

    context.deleteObject(results.firstObject as NSManagedObject)

我在这行代码中遇到错误:context.deleteObject(results.firstObject as NSManagedObject)。它说:Cannot invoke 'deleteObject' with an argument list of type '(NSManagedObject)'。有人知道我该如何解决这个错误吗?

更新:

2015-07-12 20:43:09.601 Note[4222:138125] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Unable to generate SQL for predicate (name == Test2) (problem on RHS)'
*** First throw call stack:
(
0   CoreFoundation                      0x000000010ebd6c65 __exceptionPreprocess + 165
1   libobjc.A.dylib                     0x0000000110741bb7 objc_exception_throw + 45
2   CoreData                            0x000000010e7f0bbc -[NSSQLGenerator newSQLStatementForRequest:ignoreInheritance:countOnly:nestingLevel:] + 1724
3   CoreData                            0x000000010e7dcdc4 -[NSSQLAdapter _statementForFetchRequest:ignoreInheritance:countOnly:nestingLevel:] + 244
4   CoreData                            0x000000010e6f4e0c -[NSSQLAdapter _newSelectStatementWithFetchRequest:ignoreInheritance:] + 316
5   CoreData                            0x000000010e6f4a86 -[NSSQLCore newRowsForFetchPlan:] + 118
6   CoreData                            0x000000010e6f433c -[NSSQLCore objectsForFetchRequest:inContext:] + 524
7   CoreData                            0x000000010e6f3dbb -[NSSQLCore executeRequest:withContext:error:] + 299
8   CoreData                            0x000000010e7cea6c __65-[NSPersistentStoreCoordinator executeRequest:withContext:error:]_block_invoke + 3356
9   CoreData                            0x000000010e7d7c30 gutsOfBlockToNSPersistentStoreCoordinatorPerform + 192
10  libdispatch.dylib                   0x0000000111e65614 _dispatch_client_callout + 8
11  libdispatch.dylib                   0x0000000111e4b002 _dispatch_barrier_sync_f_invoke + 365
12  CoreData                            0x000000010e7c9245 _perform + 197
13  CoreData                            0x000000010e6f3a58 -[NSPersistentStoreCoordinator executeRequest:withContext:error:] + 504
14  CoreData                            0x000000010e6f22ca -[NSManagedObjectContext executeFetchRequest:error:] + 586
15  Note                               0x000000010e4efb72 _TFC5Note14ViewController19deleteSelectedTasksfS0_FT_T_ + 738
16  Note                               0x000000010e4ef843 _TFC5Note14ViewController7delTaskfS0_FT_T_ + 51
17  Note                               0x000000010e4ef882 _TToFC5Note14ViewController7delTaskfS0_FT_T_ + 34
18  Foundation                          0x000000010f011744 __NSFireTimer + 83
19  CoreFoundation                      0x000000010eb3e174 __CFRUNLOOP_IS_CALLING_OUT_TO_A_TIMER_CALLBACK_FUNCTION__ + 20
20  CoreFoundation                      0x000000010eb3dd35 __CFRunLoopDoTimer + 1045
21  CoreFoundation                      0x000000010eaffd3d __CFRunLoopRun + 1901
22  CoreFoundation                      0x000000010eaff366 CFRunLoopRunSpecific + 470
23  GraphicsServices                    0x000000011128ca3e GSEventRunModal + 161
24  UIKit                               0x000000010f475900 UIApplicationMain + 1282
25  Note                                0x000000010e5146c7 main + 135
26  libdyld.dylib                       0x0000000111e99145 start + 1
27  ???                                 0x0000000000000001 0x0 + 1
)
libc++abi.dylib: terminating with uncaught exception of type NSException

【问题讨论】:

【参考方案1】:

问题似乎出在您的谓词定义中。请尝试:

fetchRequest.predicate = NSPredicate(format: "name = 'Test2'")

fetchRequest.predicate = NSPredicate(format: "%K = %@", "name", "Test2")

如果要添加变量。

fetchRequest.predicate = NSPredicate(format: "%K = %@", "name", variable)

【讨论】:

是的,第一个终于奏效了。非常感谢您的帮助! 我将其标记为正确。如果我想用字符串变量替换Test2,你能告诉我我必须写什么吗? (format: "name = '\(variable)'") 不起作用。 请找到我的答案已编辑。我也向你推荐这篇文章nshipster.com/nspredicate【参考方案2】:

您可以使用context.deleteObject(results?.first as! NSManagedObject),它会编译,但如果它不是 NSManagedObject,则会崩溃。

这显然不是正确的方法。请记住:! 是代码异味,因为在大多数情况下您不需要它们。

firstObject 是一个 NSArray 方法,要使用它,您应该指定results 的类型为NSArray(即let results: NSArray)。 Swift 标准库等价物是first,它返回一个可选值,而deleteObject 不接受可选值。所以你应该打开它,你可以同时检查它是否是NSManagedObject类型。

类似的东西呢:

   if let results = context.executeFetchRequest(fetchRequest, error:&error),
      let managedObject = results.first as? NSManagedObject 
         context.deleteObject(managedObject)
   

【讨论】:

我试用了你的建议。现在我的应用程序在这行代码中崩溃:if let results = context.executeFetchRequest(fetchRequest, error:&error), 并出现以下错误:Thread 1: breakpoint 1.2 3.2。这里有一些(希望是)有用的图片:dropbox.com/s/0ubnlnufodnsb2l/… 和 dropbox.com/s/5m9vdx2tlgns59o/…。希望它有助于解决错误。 您似乎在代码中设置了一些断点,而不是错误。请禁用你的断点,它应该可以工作。 我设置了一个异常断点。我禁用了它,但应用程序仍然崩溃。现在我也得到一个日志条目(见我更新的答案)。感谢您的帮助。 @agy 你知道我要做什么吗? @paro 找到我的答案

以上是关于从 Coredata 中删除一个对象(出现错误)的主要内容,如果未能解决你的问题,请参考以下文章

尝试在块中保存对象时崩溃。 (CoreData 无法满足...的错误)

如何从数据数组中删除对象(核心数据)

CoreData批删除(Batch Delete)陷阱的识别与逃脱(Could not merge changes错误等)

CoreData批删除(Batch Delete)陷阱的识别与逃脱(Could not merge changes错误等)

Core Data 对象删除使应用程序崩溃

如何从 CoreData 获取完整的对象(不是故障)?