我现在正在尝试学习ocaml,并想从一个小程序开始,生成所有的位组合:"0","0","0","0“,"1","0”……诸若此类
我的想法是以下代码:
let rec bitstr length list =
if length = 0 then
list
else begin
bitstr (length-1)("0"::list);
bitstr (length-1)("1"::list);
end;;但我得到以下错误:
Warning S: this expression should have type unit.
val bitstr : int -> string list -> string list = <fun>
# bitstr 3 [];;
- : string list = ["1"; "1"; "1"]我不知道该改什么,你能帮我吗?
向Philipp致以最好的问候
发布于 2010-05-10 21:37:42
begin foo; bar end执行foo并丢弃结果,然后执行bar。因为这只在foo有副作用并且没有有意义的返回值时才有意义,如果foo有一个非单位的返回值,ocaml会发出警告,因为其他一切都可能是程序员的错误(即程序员实际上并不打算丢弃结果)-就像这里的情况一样。
在这种情况下,使用"0“计算列表,然后将其丢弃是没有意义的。您可能想要连接这两个列表。您可以使用@运算符执行此操作:
let rec bitstr length list =
if length = 0 then
[list]
else
bitstr (length-1)("0"::list) @ bitstr (length-1)("1"::list);;请注意,我还使length = 0案例返回[list],而不仅仅是list,因此结果是一个列表列表,而不是平面列表。
发布于 2010-05-12 00:07:19
虽然sepp2k的答案是正确的,但我想添加以下替代方案(它与您提出的签名不匹配,但实际上做了您想要的):
let rec bitstr = function
0 -> [[]]
| n -> let f e = List.map (fun x -> e :: x) and l = bitstr (n-1) in
(f "0" l)@(f "1" l);;第一个不同之处在于,调用bitsr 2返回[["0"; "0"]; ["0"; "1"]; ["1"; "0"]; ["1"; "1"]]的函数不需要传递空列表。其次,它返回一个有序二进制值的列表。但更重要的是,在我看来,它更接近ocaml的精神。
发布于 2015-11-17 03:38:13
我喜欢得到其他的想法!
所以这就是..。
let rec gen_x acc e1 e2 n = match n with
| 0 -> acc
| n -> (
let l = List.map (fun x -> e1 :: x) acc in
let r = List.map (fun x -> e2 :: x) acc in
gen_x (l @ r) e1 e2 (n - 1)
);;
let rec gen_string = gen_x [[]] "0" "1"
let rec gen_int = gen_x [[]] 0 1
gen_string 2
gen_int 2结果:
[["0"; "0"]; ["0"; "1"]; ["1"; "0"]; ["1"; "1"]]
[[0; 0]; [0; 1]; [1; 0]; [1; 1]]https://stackoverflow.com/questions/2802900
复制相似问题