我想在我的Scala代码中实现操作链。我以为我可以使用“折叠”。所以,假设我的行为序列如此声明:
val chainOfActions: Seq[String => String] = Seq(
{resultFromPreviousAction =>
println("Inside the first action")
"Result from the first action"
},
{resultFromPreviousAction =>
println("Inside the second action")
resultFromPreviousAction + " > " + "Result from the second action"
}
)
上面的代码编译(我在scala控制台内部尝试过)。
接下来将应用折叠:
chainOfActions.fold("") { (intermediateText, action) =>
action(intermediateText)
}
但是上面的代码给出了以下错误:
<console>:10: error: Object does not take parameters
action(intermediateText)
嗯...为什么我的动作会失去它的类型(我期待类型为“String =&gt; String”)?
所以我尝试声明类型:
type MyBlockType = String => String
以这种方式宣布我的Seq:
val chainOfActions: Seq[MyBlockType] = Seq(
{resultFromPreviousAction =>
println("Inside the first action")
"Result from the first action"
},
{resultFromPreviousAction =>
println("Inside the second action")
resultFromPreviousAction + " > " + "Result from the second action"
}
)
仍然,得到同样的错误。所以,我试着检查“行动”的实际类型......:
chainOfActions.fold("") { (intermediateText, action) =>
println(action.getClass)
"Test it"
}
我在控制台中收到此信息:
class $line101.$read$$iw$$iw$$anonfun$1
class $line101.$read$$iw$$iw$$anonfun$2
res58: Object = Test it
所以......,这是正确的(这是一个功能)。但是为什么Scala不承认它是对象?
请帮我指出我做错的地方。
谢谢, 拉嘎
答案 0 :(得分:4)
在这种情况下,您需要&#39; foldLeft&#39;:
val result = chainOfActions.foldLeft("") {
case (intermediateText, action) => action(intermediateText)
}
对于折叠,您需要为初始值和Seq中的每个值使用相同的类型。但是您的初始(和输出)值是String,但集合是String =&gt;串
方法签名:
def fold[A1 >: A](z: A1)(op: (A1, A1) => A1): A1
def foldLeft[B](z: B)(op: (B, A) => B): B
因此,如果你想使用fold,你的初始值必须是String =&gt;字符串,例如带有标识的字符:
val result = chainOfActions.fold(identity[String] _)((l, r) => l andThen r).apply("")