我有一个集合A,我需要从集合A创建集合B.在最简单的情况下,人们可能希望使用map
方法,但我正在寻找一个解决方案,其中每一步都在要创建B的元素,需要访问集合中已有的元素。
我想到了创建B的多种可能性:
是否存在惯用法,或者至少有一种方法可以根据不同的使用案例选择一种方法?
答案 0 :(得分:6)
最惯用的是foldLeft
- 折叠在函数式编程中非常自然。另一种可能性是scanLeft
,这可能会略微减少簿记。
另一方面,这看起来真的是对State
monad的迭代。这本书Functional Programming in Scala有一些非常类似于它的练习之一。
对于函数State
,A
monad基本上是类型为S => (S, A)
的monad,尽管它通常被声明为一种正确的类型,其中包含一些特殊方法,使常见操作更容易。
在您的示例中,状态S
将是最后结果的Option[A]
(或者,如果适用,则为A
的“零”)。然后,您可以将您的集合从其T
类型映射到S => (S, A)
(或州monad类型)的函数中,获得Coll[S => (S, A)]
。
从那里你可以sequence
sequence
M[N[A]]
可以将N[M[A]]
变为M
for monads N
和S => (S, Coll[A])
- 请参阅The Essence of the Iterator Pattern),获取Coll[A]
,将其提供给初始状态,然后检索foldLeft
。
网上有很多关于州monad的资源,不过我个人觉得比大多数其他monad更难掌握。有人提到我可能是因为“州”monad被错误命名,而且它实际上是一个“状态处理器”monad,这对我来说很有意义。
无论如何,从你的选择来看,{{1}}是最惯用的,但状态monad方法非常适合这项任务。
答案 1 :(得分:5)
我肯定会认为foldLeft是最惯用的方法。这正是我在阅读你的可能性之前所想到的。