如何合并两个对象列表并标识相同的元素

时间:2019-08-30 08:07:40

标签: kotlin

我有2个包含相同类型对象的列表,我希望合并这2个列表。

让我们举个例子:

列表1包含[A, B, C, E]

List2包含[A, D]

我需要[A, B, C, E, D]

我绝对希望相同的元素(在这里是对象A)成为列表1中的那些元素。

是否保留项目顺序并不重要。

4 个答案:

答案 0 :(得分:4)

如果要保留list1中相同的元素,则不应使用distinct。您的代码应在此业务规则上明确,以避免将来出现错误。

一个例子:

class Elt(private val id: Int, private val content: String) {

    open fun equals(other: Elt): Boolean {
        return this.id == other.id
    }

    override fun toString(): String {
        return "$id -> $content"
    }
}

fun main(args: Array<String>) {
    val l1 = listOf(Elt(1,"L1"), Elt(2,"L1"), Elt(3,"L1"), Elt(4,"L1"))
    val l2 = listOf(Elt(1,"L2"), Elt(5,"L2"))

    val l4 = l2 + l1
    println(l4.distinct()) // Elt 1 comes from L2

    val l5 = l1 + l2
    println(l5.distinct()) // Elt 1 comes from L1

    val l6 = l2.toMutableList().apply { addAll(l1) }.distinct()
    println(l6.distinct()) // Elt 1 comes from L2
}

它将打印:

[1 -> L1, 2 -> L1, 3 -> L1, 4 -> L1, 1 -> L2, 5 -> L2]
[1 -> L2, 5 -> L2, 1 -> L1, 2 -> L1, 3 -> L1, 4 -> L1]
[1 -> L1, 2 -> L1, 3 -> L1, 4 -> L1, 1 -> L2, 5 -> L2]
[1 -> L2, 5 -> L2, 1 -> L1, 2 -> L1, 3 -> L1, 4 -> L1]

如果在添加元素之前在list2中删除重复项,则将确保与list1保持相同的元素:

    val l3 = l1 + (l2 - l1.intersect(l2))
    println(l3)

答案 1 :(得分:3)

简单的情况:

val lista = listOf( 1,2,3 )
val listb = mutableListOf( 1,4,5 ).apply { addAll(lista) }.distinct()
// result listb -> [1, 4, 5, 2, 3]

答案 2 :(得分:1)

添加两个字符串列表

val a = listOf("a","b" ,"c" , "e")
val b = listOf("a", "d")
val c = a + b

要仅具有不同的值,

val d = c.distinct()

答案 3 :(得分:1)

上述解决方案的替代方案:使用HashSetSet集合不支持同一元素的多次出现,因此,当您两次添加A时,第二个元素将被丢弃。

var s: HashSet<String> = HashSet<String>()
s.addAll(listOf("A", "B", "C", "E"))
s.addAll(listOf("A", "D"))
var l = s.toList()

由于HashSet在后​​台使用散列,因此大多数操作的复杂度为O(1)。