【问题标题】:Comparing and replacing items in two lists with different sizes in Kotlin?在 Kotlin 中比较和替换两个不同大小的列表中的项目?
【发布时间】:2019-04-27 21:22:33
【问题描述】:

我有以下功能:

override fun insertUpdatedItems(items: List<AutomobileEntity>) {
        if (!items.isEmpty()) {
            items.forEachIndexed { index, automobileEntity ->
                if (automobileEntity.id == items[index].id) {
                    automobileCollection[index] = items[index]
                    notifyItemInserted(index)
                }
            }
        }
    }

我用于为 recyclerview 提供数据,我正在尝试插入已在 automobileCollection 中的更新/编辑项目,其大小始终返回 10 项目,但 items 列表可能会有所不同110

它应该按id 比较项目,但我目前使用此功能得到的是已编辑的项目只是插入到 recyclerview 的适配器中,而不是被视为已经存在的项目。

相反,如果我使用 automobileCollection 进行迭代,我会得到 IndexOutOfBoundsException,因为大多数时候 items 列表小于 automobileCollection

【问题讨论】:

  • 你可以跳过外部条件。如果items 为空,则forEachIndexed 什么也不做...您用index 迭代items,然后将其与自身进行比较(automobileEntryitems 的一个元素)。有了这个找到的项目(基本上是每个),您使用该索引(项目列表!!!)来更新不相关的automobileCollection ...您实际上想要实现什么?并且请确保您理解我之前写的内容......这对于处理forEach等是必不可少的。

标签: android list collections kotlin


【解决方案1】:

要使用另一个列表中的项目更新列表,您可以使用多种方法。

首先从直接替换开始(保留顺序,但这只是一个细节):

val sourceList = TODO()
val targetList = TODO()

targetList.replaceAll { targetItem -> 
  sourceList.firstOrNull { targetItem.id == it.id } 
            ?: targetItem
}

或者删除所有项目并再次添加:

targetList.removeIf { targetItem ->
  sourceList.any { it.id == targetItem.id }
}
targetList.addAll(sourceList)

使用 listIterator(注意!当您调用 replaceAll... 时,这实际上也发生在幕后...不同的方式,但类似 ​​;-)):

val iterator = targetList.listIterator()
while (iterator.hasNext()) {
  iterator.next().apply {
    sourceList.firstOrNull { id == it.id }?.also(iterator::set)
  }
}

可能不那么可读...对于您的forEachIndexed,我真的没有看到任何用例。对于其他问题,肯定存在,但我建议您尽可能多地省略索引(以及forEach)。如果您没有想到更好的方法,那么forEach 也可以,但很多时候,forEach(更甚者是forEachIndexed)并不是解决问题的最佳方法。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-11-07
    • 1970-01-01
    • 1970-01-01
    • 2020-06-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多