NSFetchedResultsController为每个部分提供不同的排序描述符

时间:2016-01-28 11:17:32

标签: swift sorting core-data nsfetchedresultscontroller

我有NSDate属性的对象,我需要将它们分成两个部分(第一个 - 未来事件,第二个 - 历史事件)然后第一部分我需要按日期属性按升序排序它们和第二部分部分按降序排列。知道怎么做排序吗?

3 个答案:

答案 0 :(得分:2)

假设您使用的是NSFetchedResultsController,则必须以某种方式对基础提取进行排序。我可以想到两种不同的解决方案:

  1. 使用两个单独的FRC,具有互补谓词,以便一个处理过去的事件,而另一个处理未来的事件。一个将按升序排序,另一个将按降序排序。问题是两个FRC都会为第0节生成indexPaths。因此,您需要重新映射第二个FRC的indexPaths以使用tableView的第1部分。例如,在cellForRowAtIndexPath中你需要这样的东西:

    if (indexPath.section == 0) {
        objectToDisplay = self.futureFetchedResultsController.objectAtIndexPath(indexPath)
    } else { // use second FRC
        let frcIndexPath = NSIndexPath(forRow: indexPath.row, inSection: 0)
        objectToDisplay = self.pastFetchedResultsController.objectAtIndexPath(frcIndexPath)
    }
    
  2. 或者,坚持使用单个FRC,按升序排序。然后重新映射第二部分的indexPath,以便该部分中的最后一个对象显示在第0行等中:

    if (indexPath.section == 0) {
        objectToDisplay = self.fetchedResultsController.objectAtIndexPath(indexPath)
    } else { // use remap to reverse sort order FRC
        let sectionInfo = self.fetchedResultsController.sections[1] as! NSFetchedResultsSectionInfo
        let sectionCount = sectionInfo.numberOfObjects
        let frcIndexPath = NSIndexPath(forRow: (sectionCount - 1 - indexPath.row), inSection:indexPath.section)
        objectToDisplay = self.fetchedResultsController.objectAtIndexPath(frcIndexPath)
    }
    
  3. 我个人认为第二种选择更可取。在每种情况下,所有tableView数据源/委托方法都需要相同的重映射,而FRC委托方法将需要反向映射。

答案 1 :(得分:0)

要解决一般问题 - 每个部分需要不同的排序 - 您可以将多个NSFetchedResultsController对象包装到单个对象中,该对象将截面数组展平为单个数组,并重新映射函数的结果,如{{ 1}}以及func object(at: IndexPath)通知中的索引路径。

这将允许您解决想要以不同方式显示任意数量的部分的一般问题。

我开始创建这个包装器对象(CompoundFetchedResultsController),它似乎运行良好:

NSFetchedResultsControllerDelegate

答案 2 :(得分:-1)

首先在fetchRequest

中设置排序描述符
func itemFetchRequest() -> NSFetchRequest{

    let fetchRequest = NSFetchRequest(entityName: "Events")
    let primarySortDescription = NSSortDescriptor(key: "futureEvents", ascending: true)
    let secondarySortDescription = NSSortDescriptor(key: "historicEvents", ascending: false)
    fetchRequest.sortDescriptors = [primarySortDescription, secondarySortDescription]
    return fetchRequest
}

然后设置你的节数

func numberOfSectionsInTableView(tableView: UITableView) -> Int {
    let numberOfSections = frc.sections?.count
    return numberOfSections!
}

最后是你的标题

func tableView(tableView: UITableView, titleForHeaderInSection section: Int) -> String?{
    let sectionHeader = Future Events
    let sectionHeader1 = Historic Events
        if (section== "0") { 
            return sectionHeader
        } else {
            return sectionHeader1
        }
    } else {
        return nil
    }
}