假設我有一些像這樣的代碼:如何在OCAML中使用List.Map跳過一個術語?
List.map (fun e -> if (e <> 1) then e + 1 else (*add nothing to the list*))
有沒有辦法做到這一點?如果是這樣,怎麼樣?
我想同時操作該項目,如果它符合一些標準,並忽略它,如果它不。因此List.filter似乎不是解決方案。
假設我有一些像這樣的代碼:如何在OCAML中使用List.Map跳過一個術語?
List.map (fun e -> if (e <> 1) then e + 1 else (*add nothing to the list*))
有沒有辦法做到這一點?如果是這樣,怎麼樣?
我想同時操作該項目,如果它符合一些標準,並忽略它,如果它不。因此List.filter似乎不是解決方案。
SML有一個函數mapPartial,它正是這樣做的。可悲的是,這個功能在OCaml中不存在。但是你可以自己簡單地定義它是這樣的:
let map_partial f xs =
let prepend_option x xs = match x with
| None -> xs
| Some x -> x :: xs in
List.rev (List.fold_left (fun acc x -> prepend_option (f x) acc) [] xs)
用法:
map_partial (fun x -> if x <> 1 then Some (x+1) else None) [0;1;2;3]
將返回[1;3;4]
。
或者您可以使用filter_map
from extlib ygrek指出。
另外,您可以過濾列表,然後應用所得到的名單上圖如下:
let map_bis predicate map_function lst =
List.map map_function (List.filter predicate lst);;
# val map_bis : ('a -> bool) -> ('a -> 'b) -> 'a list -> 'b list = <fun>
用法:
# map_bis (fun e -> e<>1) (fun e -> e+1) [0;1;2;3];;
- : int list = [1; 3; 4]
另一個解決方案是直接使用foldl
:
let f e l = if (e <> 1)
then (e + 1)::l
else l
in List.fold_left f [] list
但我的偏好是filter_map
作爲邁克爾·
,如果你想保持他們或空列表,您也可以映射值獨居名單如果你不這樣做,然後連接結果。
List.concat (List.map (fun e -> if (e <> 1) then [e + 1] else []) my_list)
list.filter_map in extlib – ygrek 2010-07-08 11:43:49