Scala 比较列表-检查一个列表是否是第二个列表的一部分

Scala 比较列表-检查一个列表是否是第二个列表的一部分,scala,functional-programming,comparison-operators,Scala,Functional Programming,Comparison Operators,大家早上好(或晚上好:), 我无法检查一个列表是否是第二个列表的一部分。第一个列表的所有元素必须是第二个列表的第一个元素 比如说 L1=[1,2,3,4] L2=[3,4,5,6] >false L1=[1,2,3,4] L2=[1,2,3,4,5,6,7,8] >true L1=[-1,-7,3,2] L2=[1,2,3,4,5] >false 我知道使用循环然后比较元素会很容易,但我想用函数的方式来做。我有一个主意,但它并不聪明,粘贴两个列表(例如使用zip),然后解

大家早上好(或晚上好:), 我无法检查一个列表是否是第二个列表的一部分。第一个列表的所有元素必须是第二个列表的第一个元素

比如说

L1=[1,2,3,4]
L2=[3,4,5,6]
>false

L1=[1,2,3,4]
L2=[1,2,3,4,5,6,7,8]
>true

L1=[-1,-7,3,2]
L2=[1,2,3,4,5]
>false
我知道使用循环然后比较元素会很容易,但我想用函数的方式来做。我有一个主意,但它并不聪明,粘贴两个列表(例如使用zip),然后解压,chenge设置并比较它是否与第二个列表具有相同的长度,但这种方法看起来不太好

我是Scala的新手,很抱歉问了这么愚蠢的问题。我不需要代码,但需要一些建议!:)


谢谢大家

我做了类似的事情。就目前而言,它是有效的:

  def segment(L1: List[Int], L2: List[Int]) : Boolean = (L1, L2) match {
    case (h1::t1, h2::t2) if (h1 == h2) => segment(t1,t2)
    case(h1::t1, h2::t2) if (h1 != h2) => return false
    case nil => return true;
}

这是一种惯用的方法;让

val a = (1 to 5).toList    
val b = (2 to 4).toList
val c = List(2,7,4)
然后

这里,
tails
将在每个子列表上创建一个迭代器,从列表中的一个项目到列表中的最后一个项目<只有当我们感兴趣的字符串是任何子列表的开始时,code>startsWith才会成功
collectFirst
将在
startsWith
的第一次成功响应时提供一个
选项[Boolean]
,否则它将提供一个表示不匹配的
None

为了总结这个想法,考虑这个隐式类,

implicit class RichList[A](val seg: List[A]) extends AnyVal {
  def isSegmentOf(l: List[A]) = {
    l.tails.collectFirst { case t if (t.startsWith(seg)) => true }
  }
}
因此


这是一个子字符串搜索问题。有很多算法可以做到这一点:列表上甚至有一个方法可以做到这一点:
startsWith
,正如您所知:此方法的结果与您传递列表的顺序无关(so段(列表(1,2),列表(1,2,3))==段(列表(1,2,3),列表(1,2))==true。如果这是desierd,则该方法是干净的。否则,应添加case
(x::xs,Nil)=>false
,表示左侧列表应小于或等于第二个。此外,如果问题不是关于自己编写算法,那么我建议您看看用户Shadowlands评论的
startsWith
a.tails.collectFirst { case l if (l.startsWith(c)) => true }
res: Option[Boolean] = None
implicit class RichList[A](val seg: List[A]) extends AnyVal {
  def isSegmentOf(l: List[A]) = {
    l.tails.collectFirst { case t if (t.startsWith(seg)) => true }
  }
}
b.isSegmentOf(a)
res: Option[Boolean] = Some(true)

c.isSegmentOf(a)
res: Option[Boolean] = None