2017-02-16 48 views
0

需要一个提示,在花了几个小时与NSFetchedResultsController挣扎后放弃。NSFetchedResultsController:索引处没有对象2147483647

的错误信息是:

CoreData: error: NSFetchedResultsController: no object at index 2147483647 in section at index 0

...但我甚至不知道是谁发射的错误。我的代码的最后一部分是saveContext(),下一个断点位于didChange内部。

class ViewController : UITableViewController, NSFetchedResultsControllerDelegate 
private lazy var channelController: NSFetchedResultsController<ZChannel> = { 

    let appDelegate: AppDelegate = UIApplication.shared.delegate as! AppDelegate 

    let request: NSFetchRequest<ZChannel> = ZChannel.fetchRequest() 
    request.sortDescriptors = [NSSortDescriptor(key: "kit", ascending: true), NSSortDescriptor(key: "name", ascending: true)] 

    let retval: NSFetchedResultsController<ZChannel> = NSFetchedResultsController(fetchRequest: request, 
                       managedObjectContext: appDelegate.persistentContainer.viewContext, 
                       sectionNameKeyPath: "kit", 
                       cacheName: nil) 
    retval.delegate = self 

    return retval 
}() 

public init() { 
    super.init(style: .grouped) 

    self.tableView.register(ChannelTableCell.self, forCellReuseIdentifier: "ChannelTableCell") 

    let appDelegate: AppDelegate = UIApplication.shared.delegate as! AppDelegate 
    appDelegate.persistentContainer.viewContext.perform { 
     do { 
      try self.channelController.performFetch() 
     } catch { 
      let e = error as NSError 
      fatalError("[CoreData] Unresolved fetch error \(e), \(e.userInfo)") 
     } 
    } 
} 


public func controller(_ controller: NSFetchedResultsController<NSFetchRequestResult>, didChange anObject: Any, at indexPath: IndexPath?, for type: NSFetchedResultsChangeType, newIndexPath: IndexPath?) { 
    switch(type) { 
    case .insert: 
     self.tableView?.insertRows(at: [newIndexPath!], with: .bottom) 
     break; 
    case .update: 
     self.tableView?.reloadRows(at: [indexPath!], with: .bottom) 
     break 
    default: 
     break 
    } 
} 

public func controller(_ controller: NSFetchedResultsController<NSFetchRequestResult>, didChange sectionInfo: NSFetchedResultsSectionInfo, atSectionIndex sectionIndex: Int, for type: NSFetchedResultsChangeType) { 
    switch (type) { 
    case .insert: 
     self.tableView?.insertSections(IndexSet(integer: sectionIndex), with: UITableViewRowAnimation.bottom) 
     break 
    case .delete: 
     self.tableView?.deleteSections(IndexSet(integer: sectionIndex), with: UITableViewRowAnimation.bottom) 
     break 
    default: 
     break 
    } 
} 

从另一个线程我插入新的对象:

self.persistentContainer.viewContext.performAndWait 
{ 
    // ... 
    let channel: ZChannel = NSEntityDescription.insertNewObject(forEntityName: "ZChannel", into: self.persistentContainer.viewContext) as! ZChannel 
    // ... 
    self.saveContext() 
} 
+0

哪里UITableViewDataSource和NSFetchedResultsControllerDelegate方法吗? – Mannopson

回答

1

的一些问题:

  • 2147483647是NSNotFound。如果你正在使用类似indexOfObject的东西,并假设它在数组中,然后使用那个会导致崩溃的索引。
  • 当您使用newIndexPath时,您正在使用indexPath进行行更新。原因是indexPath是插入或删除之前的索引,newIndexPath是插入和删除之后的索引。
  • 没有理由叫self.channelController.performFetch()persistentContainer.viewContext.perform你已经在主线程
相关问题