T.M*_*T.M 1 f# f#-interactive f#-3.0 f#-data
任何人都可以用非常简单的方式解释 F# 中的 List.Fold 和 List.Foldback 是什么。我读了几本书,并试图在网上搜索一个简单的解释,但我仍然不明白。
- 这不是一个重复的问题,也没有在另一个链接中回答。
理解它的最好方法是通过一个例子。想象一下,你有一个数字列表,你想找出总数。在命令式编程中,您可以这样做:
let numbers = [ 19 ; 52 ; 35 ; 27]
let mutable total = 0
for n in numbers do
total <- total + n
printfn "%A" total // 133
Run Code Online (Sandbox Code Playgroud)
这是一个很好的解决方案,但不起作用。让我们List.fold来做同样的事情:
numbers
|> List.fold (fun total n -> total + n) 0
|> printfn "%A" // 133
Run Code Online (Sandbox Code Playgroud)
瞧!如果你眯着眼睛,你可以在两种解决方案中识别出相同的元素。
totaltotal + n0让我们看看 的签名List.fold:
val List.fold:
folder: 'State -> 'T -> 'State ->
state : 'State ->
list : 'T list
-> 'State
Run Code Online (Sandbox Code Playgroud)
看看元素是如何匹配的?
List.foldBack是相同的,但元素以相反的顺序馈送。参数的顺序也不同。
有趣的事情之一fold是,在许多情况下,它可以代替尾递归函数:
如果你没有List.fold并且想实现一个totalF没有 mutable的函数,你会怎么做?你需要递归,更好的是尾递归:
let rec totalF total ns =
match ns with
| [] -> total
| n :: tail -> totalF (total + n) tail
numbers
|> totalF 0
|> printfn "%A" // 133
Run Code Online (Sandbox Code Playgroud)
同样,您可以像以前一样看到所有元素。事实上,如果我们做成total + n一个参数totalF:
let rec totalF f total ns =
match ns with
| [] -> total
| n :: tail -> totalF f (f total n) tail
numbers
|> totalF (fun total n -> total + n) 0
|> printfn "%A" // 133
Run Code Online (Sandbox Code Playgroud)
你得到fold,签名和使用是一样的:
val totalF:
f : 'a -> 'b -> 'a ->
total: 'a ->
ns : 'b list
-> 'a
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
2959 次 |
| 最近记录: |