在 Swift 中自动重新排序核心数据

Posted

技术标签:

【中文标题】在 Swift 中自动重新排序核心数据【英文标题】:Automatic re-ordering of Core Data in Swift 【发布时间】:2015-01-30 19:58:30 【问题描述】:

在“编辑模式”下移动单元格时,我试图重新排序我的核心数据列表。 Obj-c 在这方面的讨论似乎很有帮助(见下面的链接),但我在 Swift 中找不到任何东西。

有没有人遇到过 Swift 的相关文档?或者有人愿意将 obj-c 代码翻译成 Swift 吗?谢谢!

Obj-c 链接:

How can I maintain display order in UITableView using Core Data?

How to implement re-ordering of CoreData records?

【问题讨论】:

我投票结束这个问题,因为 *** 不是翻译服务。一般来说,在可预见的未来,Swift 开发至少需要能够阅读 Objective-C。试一试,然后提出具体问题。 这里有两个问题,不是吗?你不能把翻译的问题删掉吗? 【参考方案1】:

这是一个不错的方法。它还会检查目标是否可能不包含任何数据,您还可以跨部分移动。 isMoving 将禁止委托触发。您的实体还需要一个 sortorder 属性。

private func indexIsOutOfRange(indexPath:NSIndexPath) -> Bool 
    if indexPath.section > self.fetchedResultsController.sections!.count - 1 
        return true
    
    if indexPath.row > self.fetchedResultsController.sections![indexPath.section].objects!.count - 1 
        return true
    
    return false


override func tableView(tableView: UITableView, moveRowAtIndexPath sourceIndexPath: NSIndexPath, toIndexPath destinationIndexPath: NSIndexPath)

    if indexIsOutOfRange(destinationIndexPath) 
        return
    

    isMovingItem = true


    if sourceIndexPath.section == destinationIndexPath.section 
        if var todos = self.fetchedResultsController.sections![sourceIndexPath.section].objects 
            let todo = todos[sourceIndexPath.row] as! FoodEntry
            todos.removeAtIndex(sourceIndexPath.row)
            todos.insert(todo, atIndex: destinationIndexPath.row)

            var idx = 1
            for todo in todos as! [FoodEntry] 
                todo.sortOrder = NSNumber(integer: idx++)
            
            try!managedObjectContext.save()
        
     else 

        if var allObjectInSourceSection = fetchedResultsController.sections![sourceIndexPath.section].objects 
            let object = allObjectInSourceSection[sourceIndexPath.row] as! FoodEntry
            allObjectInSourceSection.removeAtIndex(sourceIndexPath.row)

            for (index,object) in (allObjectInSourceSection as! [FoodEntry]).enumerate() 
                object.sortOrder = NSNumber(integer: index)
            


            if var allObjectInDestinationSection = fetchedResultsController.sections![destinationIndexPath.section].objects 

                allObjectInDestinationSection.insert(object, atIndex: destinationIndexPath.row)

                for (index,object) in (allObjectInDestinationSection as! [FoodEntry]).enumerate() 
                    object.sortOrder = NSNumber(integer: index)
                    object.section = NSNumber(integer: destinationIndexPath.section)
                
            
        

    


    dispatch_async(dispatch_get_main_queue(),  () -> Void in
        tableView.reloadRowsAtIndexPaths(tableView.indexPathsForVisibleRows!, withRowAnimation: .Fade)
    )

    isMovingItem = false

    try!managedObjectContext.save()

    fetch()


【讨论】:

Timm,我已经实现了这种方法,并做了一些小的改动。一个是我确实使用了 reloadRoasAtIndexPath,我让 didChange anObject 方法处理重新加载。我很好奇 isMovingItem 的作用,当我将代码注释掉时,一切正常。显然我的代码是不同的,但如果你能简要解释一下最有帮助的用法。 +1 顺便说一句

以上是关于在 Swift 中自动重新排序核心数据的主要内容,如果未能解决你的问题,请参考以下文章

使用 NSFetchedResultsController 核心数据重新排序 TableView 单元格 - Swift 3

如何在 swift 中使用 fetchedresultscontroller 重新排序 tableview 行?

如何在swift 4中重新排序单元格后保存tableView顺序

使用 NSPredicate 对表视图中的核心数据进行排序 (Swift)

Swift - 按部分对核心数据进行排序

从核心数据中按日期对 TableView 进行排序 - Swift4