Amitabh Ranjan
Amitabh Ranjan

Reputation: 1500

How to combine elements of multiple lists in scala

I am new to Scala. I have three List.

List("XX", None,None,None)

List( None,"YY",None,None)

List(None,None,None, "ZZ")

I need to merge these list to create a single list which should look like

List("XX","YY",None,"ZZ")

Is there any way in scala to achieve this result? Thanks

Upvotes: 0

Views: 1560

Answers (4)

Seth Tisue
Seth Tisue

Reputation: 30453

Your lists are List[AnyRef]. That's a type that should never appear in ordinary Scala code.

I would suggest representing your data using List[Option[String]]:

scala> List(List(Some("XX"), None, None, None),
     |      List(None, Some("YY"), None, None),
     |      List(None, None, None, Some("ZZ")))
res2: List[List[Option[String]]] = List(...

Now your problem is easy to solve:

scala> res2.transpose.map(_.flatten.headOption)
res6: List[Option[String]] = List(Some(XX), Some(YY), None, Some(ZZ))

I've assumed here that if there are multiple Somes in the same position, you want to take the first one.

Upvotes: 3

elm
elm

Reputation: 20415

For

val xs = List(list1,list2,list2)

consider

xs.flatten.distinct

Upvotes: 2

Shyamendra Solanki
Shyamendra Solanki

Reputation: 8851

val l1 = List("XX", None, None, None)
val l2 = List(None, "YY", None, None)
val l3 = List(None, None, None, "ZZ")

val listOfList = List(l1, l2, l3) 

// Assuming all lists are of same length.

val lT = listOfList.transpose  // swap column and rows
val result = lT.map{ _.reduce{ (a, b) => 
  if (a.toString == "None") b else a
}}
// List[Serializable] = List(XX, YY, None, ZZ)

Upvotes: 2

Nyavro
Nyavro

Reputation: 8866

Maybe you need this?

val list: List[List[Option[String]]] = List(
  List(Some("XX"), None, None, None),
  List(None, Some("YY"), None, None),
  List(None, None, None, Some("ZZ"))
)
list.tail.foldLeft(list.head) {
  case (acc, item) => acc.zip(item).map {
    case (Some(x), _) => Some(x)
    case (_, y) => y
  }
}

Upvotes: 5

Related Questions