使用OCaml/核心模块的惯用方法?

使用OCaml/核心模块的惯用方法?,ocaml,Ocaml,我在遵循使用核心库的真实OCaml时编写了以下函数 open Core.Core_list open Core.Option open Core.Std open Re2 let getMaxFilename target = let Ok pat = Regex.create "^.*(..)\\.txt$" in Sys.ls_dir target |> List.map ~f:(Regex.find_submatches pat) |>

我在遵循使用核心库的真实OCaml时编写了以下函数

open Core.Core_list
open Core.Option
open Core.Std
open Re2

let getMaxFilename target = 
    let Ok pat = Regex.create "^.*(..)\\.txt$" in
    Sys.ls_dir target |> 
    List.map    ~f:(Regex.find_submatches pat) |>
    List.filter ~f:is_ok |>
    List.map    ~f:(fun x -> ok_exn x |> Array.to_list |> (Fn.flip nth_exn) 1 |> fun x -> value_exn x) |>
    List.reduce ~f:max

在我看来,这看起来很混乱,因为我在顶部有很多“打开”,我必须在我使用的所有函数中命名List、Array、Sys、Fn和其他模块的名称。这是编写OCaml的“正确”方法吗?有没有一种标准的风格可以省去这些呢?

我不确定这是最好的方式,但这里有一个相当直接的风格清理,没有真正做任何实质性的工作

open Core.Std
module Regex = Re2.Regex

let get_max_filename target = 
  let pat = Regex.create_exn "^.*(..)\\.txt$" in
  Sys.ls_dir target
  |> List.map ~f:(Regex.find_submatches pat)
  |> List.filter_map ~f:Result.ok
  |> List.filter_map ~f:(fun x -> x.(1))
  |> List.reduce ~f:max
一般来说,大量使用
open
是不可取的

下面的内容可能更清晰、更容易理解

let get_max_filename target = 
  let pat = Regex.create_exn "^.*(..)\\.txt$" in
  Sys.ls_dir target
  |> List.filter_map ~f:(fun entry ->
      match Regex.find_submatches pat entry with
      | Error _ -> None
      | Ok ar -> ar.(1))
  |> List.reduce ~f:max

这里不需要前两行:Core.Core\u list是Core.Std.list的别名,Core.Option是Core.Std.Option的别名。因此,我通常使用
opencore
opencore.Std
,并且fun@Kakadu为什么不将其作为答案发布?@Kakadu我尝试了
opencore
opencore.Std
,但我无法访问
flip
nth
等功能。听起来我仍然需要命名许多模块。这是编写Ocaml代码的正确方法吗?@Ana,我喜欢详细地编写
List.nth
,以确定函数来自哪个模块。当然,我们应该在可读性和冗长性之间找到平衡的方法。@lukstafi,我的帖子似乎更像是
小提示
,而不是
完整答案