为了更好地学习 Scala,我正在玩一些基本的编程练习,但我一直在试图弄清楚为什么我的代码不会进行类型检查。
症结在于possibilities
功能。我想要一个函数,它返回一个流,其中包含给定数字列表的所有可能的数字排列和数学运算符。
我很困惑,因为将函数的返回类型更改为Stream[Object]
可以很好地读取类型检查并返回似乎是方程流的结果。但是,下面包含的版本没有类型检查,返回类型possibilites
设置为Stream[Equation]
。
附带说明一下,我知道在 opsMix 中附加卡片不会将Operation
s 置于正确的顺序,但我想先解决这部分问题。我想我会使用flatMap
or zipAll
withflatten
来完成那部分。
另外 -这不是家庭作业!
abstract class Operation
case class Add() extends Operation
case class Subtract() extends Operation
case class Multiply() extends Operation
case class Divide() extends Operation
case class Num(val valu: Float) extends Operation
type Equation = List[Operation]
def calc(equa: Equation): Float =
equa match {
case Num(x) :: List() => x
case Num(x) :: y :: Num(z) :: xs => y match {
case Add() => calc( Num(x + z)::xs )
case Subtract() => calc( Num(x - z)::xs )
case Multiply() => calc( Num(x * z)::xs )
case Divide() => calc( Num(x / z)::xs )
}
case _ => 0
}
// from http://stackoverflow.com/questions/1070859/listing-combinations-with-repetitions-in-scala
def mycomb[T](n: Int, l: List[T]): List[List[T]] =
n match {
case 0 => List(List())
case _ => for(el <- l;
sl <- mycomb(n-1, l dropWhile { _ != el } ))
yield el :: sl
}
def comb[T](n: Int, l: List[T]): List[List[T]] = mycomb(n, l.removeDuplicates)
val ops = List(Add, Subtract, Multiply, Divide)
def possibilities(cards: List[Num]) : Stream[Equation] =
{ for {
hand <- cards.permutations
opMix <- comb(cards.length-1, ops)
} yield hand ++ opMix
}.toStream
// test value:
val ppp = possibilities(List(Num(20), Num(3), Num(7), Num(100)))