【问题标题】:Scala - diff two list of case classes by subset of fieldsScala - 按字段子集区分两个案例类列表
【发布时间】:2018-02-06 20:40:30
【问题描述】:

给定两个案例类别列表

case class Entity(field1: String, field2: String, field3: String)
val a: Seq[Entity] = ...
val b: Seq[Entity] = ...

如何查找 a 中不在 b 中的所有实体,仅基于 field1 和 field2,而忽略 field3?

我已经考虑过覆盖 case 类的 equals() 函数,也是 case class ()(此处忽略字段)方法的巧妙技巧,但不同用途需要这些字段的多种组合案例,例如diff 使用 field1 + field2,然后使用 field 1 + field 3,等等......

【问题讨论】:

  • 我不会覆盖 equals,因为这不直观。如果您创建一组实体(E(a, b, c), E(a, b, d))并且只添加其中一个,因为第二个被认为是相等的......

标签: scala collections


【解决方案1】:

使用整数而不是字符串,以便于测试:

def similar (e: Entity, f: Entity) = { e.field1 == f.field1 && e.field2 == f.field2 }

scala> a
res60: Seq[Entity] = List(Entity(1,2,3), Entity(1,3,4), Entity(4,6,8), Entity(3,4,5))

scala> b
res61: Seq[Entity] = List(Entity(1,3,5), Entity(4,6,8), Entity(4,9,25))

scala> a.filter (aa => {! b.exists {bb => similar (aa, bb)} })
res62: Seq[Entity] = List(Entity(1,2,3), Entity(3,4,5))

【讨论】:

    【解决方案2】:

    您可以使用!b.exists()过滤具有特定条件的a

    case class Entity(field1: String, field2: String, field3: String)
    val a = Seq(Entity("1", "p", "x"), Entity("2", "q", "y"), Entity("3", "r", "z"))
    val b = Seq(Entity("1", "p", "x"), Entity("2", "q", "x"), Entity("3", "s", "z"))
    
    a.filter( elA => 
      !b.exists(elB => elB.field1 == elA.field1 && elB.field2 == elA.field2)
    )
    // res1: Seq[Entity] = List(Entity(3,r,z))
    

    【讨论】:

      【解决方案3】:
        val bad = b.iterator.map { x => x.field1 -> x.field2 }.toSet
        val filtered = a.filterNot { x => bad(x.field1 -> x.field2) }
      

      【讨论】:

        【解决方案4】:

        创建一个仅对您要进行比较的字段感兴趣的实体映射类:

        class EntityMap1_2( e: Entity ) {
          override def equals( o: Any ): Boolean = ???
          override def hashCode: Int = ???
        }
        

        它仅根据字段 1 和 2 定义 equalshashCode。然后您可以填充各自的集合并找出差异。

        与其他字段组合类似。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-10-19
          • 2013-04-11
          • 2019-09-09
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多