将数据类型转换为字符串 (SML)

fro*_*oli 5 sml type-conversion

我有一个返回 a 的函数(char * int) list list,例如[[(#"D", 3)], [(#"F", 7)]],现在我想知道是否可以将其转换为字符串,以便我可以使用 I/O 并将其读取到另一个文件?

mic*_*kig 5

首先,我假设您的意思是像[[(#"D", 3)], [(#"F", 7)]](注意额外的括号)这样的值,因为 SML 需要在元组构造周围加上括号。OCaml 使用稍微不同的语法,并且只允许使用逗号,例如a, b, 来构造元组。我提到这一点是因为接下来的内容完全特定于标准机器学习,不适用于 OCaml,因为我相信在 OCaml 中你最好的选择是一种完全不同的方法,我不太了解(宏,即 ocamlp4/ 5)。所以我认为这只是一个错字,并且您对标准机器学习感兴趣。

现在,不幸的是toString,标准 ML 中没有通用功能。像这样的东西必须在语言和实现中有某种特殊的支持,因为不可能用 type 编写函数'a -> string。您基本上必须toString : t -> string为每种类型编写自己的代码t

可以想象,这很快就会变得乏味。我花了一点时间研究的选项(这和其他样板功能,如compare : 't * 't -> order),并没有在文件中提出“仿制药的工作ML'er”(一个非常有趣的技术http://dl.acm.org/ citation.cfm?id=1292547)但它非常先进,我永远无法真正编译代码(也就是说这篇论文非常有趣)该论文中描述的完整泛型库位于 MLton lib repo(https:// github.com/MLton/mltonlib/tree/master/com/ssh/generic/unstable)。也许你会有更好的运气?

恕我直言,这是一种重量稍轻但功能较弱但更易于理解的方法。我在阅读那篇论文并努力让它发挥作用后写了这篇文章。这个想法是为toString函数(show在这种情况下称为)编写构建块,并将它们与其他函数组合成您自己的类型。

structure Show =
   struct
      (* Show.t is the type of toString functions *)
      type 'a t = 'a -> string

      val int: int t = Int.toString

      val char: char t = Char.toString

      val list: 'a t -> 'a list t =
       fn show => fn xs => "[" ^ concat (ExtList.interleave (map show xs) ",") ^ "]"

      val pair: 'a t * 'b t -> ('a * 'b) t =
       fn (showa,showb) => fn (a,b) => "(" ^ showa a ^ "," ^ showb b ^ ")"

      (* ... *)
   end
Run Code Online (Sandbox Code Playgroud)

由于您的类型实际上没有任何用户定义的数据类型,因此toString使用此结构编写函数非常容易:

local
   open Show
in
   val show : (char * int) list list -> string = list (list (pair (char, int)))
end

- show [[(#"D", 3)], [(#"F", 7)]] ;
val it = "[[(D,3)],[(F,7)]]" : string
Run Code Online (Sandbox Code Playgroud)

我喜欢这一点的是,组合函数读起来就像翻过来的类型。这是一种非常优雅的风格,我不能相信它,因为我从上面链接的泛型论文中得到了它。

其余代码Show(以及Eq用于相等比较的相关模块)在这里:https : //github.com/spacemanaki/lib.sml