gpt4 book ai didi

scala - Scala 匿名函数中的模式匹配

转载 作者:行者123 更新时间:2023-12-04 12:49:51 31 4
gpt4 key购买 nike

我是 Scala 开发新手,在 Paul Chiusano 编写的“Scala 函数式编程”一书中进行的编码练习 (5.12) 中遇到了问题。

我这里有这个函数,称为unfold,它接受一个初始状态和一个用于生成具有下一个状态的流的函数:

def unfold[A,S](z: S)(f: S => Option[(A,S)]): Stream[A] = f(z) match {
case Some((h,t)) => h #:: unfold(t)(f)
case _ => Stream.empty
}

例如,使用此函数可以创建无限的对象流,例如

def constant[A](a: A): Stream[A] = unfold(a)(_ => Some(a,a))

现在,我想创建斐波那契数列,然后输入:

def fibs: Stream[Int] = unfold((0,1))((a,b) => Some(a,(b,a+b)))

我收到这些错误:

  • 缺少参数类型 b

  • Some[((Int,Int),(Nothing,String))] 类型的表达式不符合预期类型 Option[(A_,(Int,Int))]

    <

如果我在传递给 unfold 的匿名函数中使用 case 关键字,例如:

{ case (a,b) => Some(a,(b,a+b))}

一切都很好。

所以我的问题是:这两种实现之间有什么区别?是关于类型推断的一些我不明白的事情吗?

最佳答案

 { (a,b) => Some(a, (b, a+b)) }

是一个接受两个参数的函数——ab,并返回一个选项(一个元组)。这不是你需要的。您想要定义一个接受单个(元组)参数的函数。一种方法是这样的:

 { tuple => Some(tuple._1, (tuple._2, tuple._1 + tuple._2)) }

你可以把它扩展成这样:

 { tuple => 
val a = tuple._1
val b = tuple._2
// Can also do it shorter, with automatic unapply here:
// val (a,b) = tuple
// this is already pretty similar to what you have with `case`, right?
Some(a, (b, a+b))
}

这看起来很长,但是 scala 有一个特殊的语法结构,可以让你“动态”地将复杂参数解构为匿名函数,使用类似于模式匹配的语法(它实际上是调用 unapply输入,与模式匹配相同):

 { case(a, b) => Some(a, (b, a+b)) }

这和上面的完全一样。

关于scala - Scala 匿名函数中的模式匹配,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40657204/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com