【问题标题】:Scala - Combine two lists in an alternating fashionScala - 以交替方式组合两个列表
【发布时间】:2013-11-06 11:29:57
【问题描述】:

如何在 Scala 中以交替方式合并 2 个列表的方式使结果列表包含 2 个列表的元素。

输入:

val list1 = List("Mary", "a", "lamb")

val list2 = List("had", "little")

输出:

List("Mary", "had", "a", "little", "lamb")

【问题讨论】:

标签: list scala


【解决方案1】:

您要查找的内容通常称为“intersperse”或“intercalate”,有几种方法可以做到:

def intersperse[A](a : List[A], b : List[A]): List[A] = a match {
  case first :: rest => first :: intersperse(b, rest)
  case _             => b
}

你也可以使用scalaz

import scalaz._
import Scalaz._

val lst1 = ...
val lst2 = ...

lst1 intercalate lst2

编辑:您还可以执行以下操作:

lst1.zipAll(lst2,"","") flatMap { case (a, b) => Seq(a, b) }

想一想,我相信最后一个解决方案是我最喜欢的,因为它最简洁但仍然清晰。如果您已经在使用 Scalaz,我会使用第二种解决方案。然而,第一个也非常易读。

为了让这个答案更完整,添加@Travis Brown 的通用解决方案:

list1.map(List(_)).zipAll(list2.map(List(_)), Nil, Nil).flatMap(Function.tupled(_ ::: _))

【讨论】:

  • 如果列表长度不同,您的最后一个解决方案将无法正常工作——您需要更不优雅的list1.map(List(_)).zipAll(list2.map(List(_)), Nil, Nil).flatMap(Function.tupled(_ ::: _))
  • @yan:当第一个列表为空时,第一个解决方案失败。
  • @TravisBrown 修复了最后一个解决方案,同时仍然有点优雅(虽然不是通用的)
  • @raHul 怎么样? intersperse(Nil, List(1,2,3)) => List(1, 2, 3)
  • @yan:线程“main”中的异常 java.lang.UnsupportedOperationException:空列表的尾部。这是我得到的例外
【解决方案2】:
val list1 = List("Mary", "a", "lamb")
val list2 = List("had", "little")

def merge1(list1: List[String], list2: List[String]): List[String] = {
    if (list1.isEmpty) list2
    else list1.head :: merge(list2, list1.tail)
}

def merge2(list1: List[String], list2: List[String]): List[String] = list1 match {
    case List() => list2
    case head :: tail => head :: merge(list2, tail)
} 

merge1(list1, list2)
merge2(list1, list2)
//> List[String] = List(Mary, had, a, little, lamb)

【讨论】:

  • 如果你匹配列表的结构而不是使用headtail,这会更好。
  • ty,添加了匹配的版本
  • @arkonautom,我不认为这是 Travis Brown 的想法。检查我的答案是否匹配结构
  • @yan 你的确实更好......几乎做到了,+1 ;)
【解决方案3】:
list1.zipAll(list2,"","").flatMap(_.productIterator.toList).filter(_ != "")

【讨论】:

    【解决方案4】:

    你可以这样做:

    def alternate[A]( a: List[A], b: List[A] ): List[A] = {
        def first( a: List[A], b: List[A] ): List[A] = a match {
            case Nil => Nil
            case x :: xs => x :: second( xs, b )
        }
    
        def second( a: List[A], b: List[A] ): List[A] = b match {
            case Nil => Nil
            case y :: ys => y :: first( a, ys )
        }
    
        first( a, b )
    }    
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-03-01
      • 2014-10-02
      • 2011-11-29
      • 2013-04-16
      • 2019-11-22
      • 1970-01-01
      • 2022-12-08
      • 1970-01-01
      相关资源
      最近更新 更多