我正在尝试从Map
. 这就是我所做的:
Map.fold (fun state key value -> state::value) [] [("one", 1); ("two", 2)]
但是,该位state::value
会产生此错误:
tryout.fs(146,48): error FS0001: Type mismatch. Expecting a
'a
but given a
'a list
我的代码有什么问题?
我正在尝试从Map
. 这就是我所做的:
Map.fold (fun state key value -> state::value) [] [("one", 1); ("two", 2)]
但是,该位state::value
会产生此错误:
tryout.fs(146,48): error FS0001: Type mismatch. Expecting a
'a
but given a
'a list
我的代码有什么问题?
其他人已经发布了很好的解决方案,所以只是为了回答你的问题并解释你的代码有什么问题——因为你正在使用Map.fold
我假设你的数据源实际上是一个地图而不是一个列表:
let sample = Map.ofSeq [("one", 1); ("two", 2)]
这是您的原始解决方案,并且可以并排工作:
// Original version - attempts to add 'state' as the new head of a list 'value'
Map.fold (fun state key value -> state::value) [] sample
// Corrected version - adds 'key' as the new head of a list 'state'
Map.fold (fun state key value -> key::state) [] sample
关键是::
运算符需要string
在左侧有一个值(此处),右侧有另一个列表(此处string list
)。您正确地创建了一个空列表[]
作为初始状态。
当您想在折叠过程中添加新键时,您需要将现有列表 ( state
) 作为右参数传递,::
并将新键 ( key
) 作为左参数传递 - 以创建一个包含键作为第一个元素的新列表,并且所有剩余的元素作为列表的其余部分(tail)。
所以 1)::
事物的参数顺序和 2)你想收集键而不是值,但如果你正在收集值,它会以相同的方式工作。
两个问题:
- 你传递的不是地图而是列表。
- 状态(你的键被折叠成的结果)和值(一个 int)被反转。
您可以将列表转换为地图(请参阅 Daniel 的评论):
["one", 1; "two", 2]
|> Map.ofList
|> Map.fold (fun state key value -> value :: state) [];;
// val it : int list = [2; 1]
或者,您可以折叠元组列表:
["one", 1; "two", 2]
|> List.fold (fun state (key, value) -> value :: state) [];;
// val it : int list = [2; 1]