List 函数将“(';a列表*b';列表)列表”展平到“';列表*';OCaml中的b列表

List 函数将“(';a列表*b';列表)列表”展平到“';列表*';OCaml中的b列表,list,functional-programming,ocaml,List,Functional Programming,Ocaml,我需要OCaml中的一个函数,它将采用 ('a list*b'list)列表及其制作 “a列表*b”列表。我试过使用内置函数List.flatte和List.concat,但它们不起作用,它们需要一种类型的'c List。有人能帮我吗?您可以使用左折功能来完成,如下所示: 您首先使用两个空列表作为累加器。对于输入列表中的每个子列表,将元素添加到相应的累加器中(第一个累加器中第一个子列表的元素和第二个子列表的元素) #让l变平= let(l1,l2)= List.fold_左(乐趣(l1,l2)(

我需要OCaml中的一个函数,它将采用
('a list*b'list)列表及其制作

“a列表*b”列表
。我试过使用内置函数List.flatte和List.concat,但它们不起作用,它们需要一种类型的
'c List
。有人能帮我吗?

您可以使用左折功能来完成,如下所示:

您首先使用两个空列表作为累加器。对于输入列表中的每个子列表,将元素添加到相应的累加器中(第一个累加器中第一个子列表的元素和第二个子列表的元素)

#让l变平=
let(l1,l2)=
List.fold_左(乐趣(l1,l2)(x,y)->
(x::l1,y::l2))([],[])l in
List.rev(List.flatte l1)、List.rev(List.flatte l2);;
val展平:('a list*'b list)list->'a list*'b list=
# 

您可以使用如下功能进行操作:

您首先使用两个空列表作为累加器。对于输入列表中的每个子列表,将元素添加到相应的累加器中(第一个累加器中第一个子列表的元素和第二个子列表的元素)

#让l变平=
let(l1,l2)=
List.fold_左(乐趣(l1,l2)(x,y)->
(x::l1,y::l2))([],[])l in
List.rev(List.flatte l1)、List.rev(List.flatte l2);;
val展平:('a list*'b list)list->'a list*'b list=
# 

以下各项应起作用:

let split2 l = (List.map fst l, List.map snd l)
let flatten2' (l1, l2) = (List.flatten l1, List.flatten l2)
let flatten2 l = flatten2' (split2 l)
在这里,
split2
将把
('a list*'b list)list
变成
('a list*'b list)
fst
snd
分别返回一对中的第一个和第二个分量)并且
flatt2'
将分别展平这两个分量。而
2
最终将满足您的需求。您也可以将其打包到单个函数中,但我认为这更容易理解


请注意,
List.map
List.flatte
都不是尾部递归的;如果您需要尾部递归版本,还有其他库也有它们,或者您可以使用
rev_xxx
函数从标准库中构建它们,或者从头开始编写它们。

以下应该可以使用:

let split2 l = (List.map fst l, List.map snd l)
let flatten2' (l1, l2) = (List.flatten l1, List.flatten l2)
let flatten2 l = flatten2' (split2 l)
在这里,
split2
将把
('a list*'b list)list
变成
('a list*'b list)
fst
snd
分别返回一对中的第一个和第二个分量)并且
flatt2'
将分别展平这两个分量。而
2
最终将满足您的需求。您也可以将其打包到单个函数中,但我认为这更容易理解


请注意,
List.map
List.flatte
都不是尾部递归的;如果您需要尾部递归版本,还有其他库也有它们,或者您可以使用
rev_xxx
函数从标准库中构建它们,或者从头开始编写它们。

您必须使用函数
List.split
List.flatte

 let my_function l =
   let (fst_list, snd_list) = List.split l in
   List.flatten fst_list, List.flatten snd_list ;;

首先,
split
函数将生成并
一个列表
和一个
'b列表
,然后您只需
展平它们。

您必须使用函数
list.split
列表.展平

 let my_function l =
   let (fst_list, snd_list) = List.split l in
   List.flatten fst_list, List.flatten snd_list ;;

首先,
split
函数将生成并
'列表
'b列表
,然后您只需
展平它们。

不幸的是,元组没有映射,您需要分解-例如,使用split and flatte:

let splcat x = match List.split x with | (a,b) -> (List.flatten a, List.flatten b) ;;
这就是命令行上的外观:

utop # splcat [([1;2],["a"]); ([3],["uvw";"xyz"]) ] ;;
- : int list * bytes list = ([1; 2; 3], ["a"; "uvw"; "xyz"])     

不幸的是,元组没有映射,您需要分解-例如,使用拆分和展平:

let splcat x = match List.split x with | (a,b) -> (List.flatten a, List.flatten b) ;;
这就是命令行上的外观:

utop # splcat [([1;2],["a"]); ([3],["uvw";"xyz"]) ] ;;
- : int list * bytes list = ([1; 2; 3], ["a"; "uvw"; "xyz"])     

这是可以的,但我需要做一些事情
('a list*'b list)list->'a list*'b list
,而不是
('a*'b)list->'a list*'b list
,但它仍然不是我需要的:(顺序不是那么重要,重要的是函数中的输入是什么。你给出的
('a*'b)列表->“a列表*”b列表
我需要
(“a列表*”b列表)list->“a list*”b list
请看我的答案,该函数具有例外类型。您似乎对OCaml非常了解,该函数我需要完成我在此处发布的另一个练习,但即使这样,它也不起作用,如果您有时间,如果您可以查看一下该函数,那就太好了。我正在为此工作数天我仍然没有答案:/这没问题,但我需要做一些事情
('a list*'b list)list->'a list*'b list
,而不是
('a*'b)list->'a list*'b list
,但它仍然不是我需要的:(顺序不是那么重要,重要的是函数中的输入是什么。你给出的
('a*'b)列表->“a列表*”b列表
我需要
(“a列表*”b列表)list->“a list*”b list
请看我的答案,该函数具有例外类型。您似乎对OCaml非常了解,该函数我需要完成我在此处发布的另一个练习,但即使这样,它也不起作用,如果您有时间,如果您可以查看一下该函数,那就太好了。我正在为此工作数天我仍然没有答案:/