【发布时间】:2015-02-15 15:10:59
【问题描述】:
在我的 OCaml 程序中,我花费大量时间一遍又一遍地为变体类型编写“to_string”。我需要它们来进行调试,或者因为我需要特定的格式化输出。
到目前为止,他们遵循如下模板:
let rec to_string = function
| Var x -> x
| Implies (f1, f2) -> Printf.sprintf "(=> %s %s)" (to_string f) (to_string f2)
| And (f1, f2) -> Printf.sprintf "(& %s %s)" (to_string f1) (to_string f2)
| Or (f1, f2) -> Printf.sprintf "(| %s %s)" (to_string f1) (to_string f2)
| Not (f) -> Printf.sprintf "(~ %s)" (to_string f)
| True -> "#t"
| False ->"#f"
我想知道是否有比这更方便/传统的方法,可能是语言的最新发展。例如,根据类型自动生成模板?可用于调试的通用打印函数?
“Real World OCaml”中提倡的一种方法是使用 Core 库的 Sexp 模块,该模块为此目的提供了便利。如果您不需要对如何打印值进行太多自定义,它似乎工作得很好。我想知道是否有其他/更好的选择。
【问题讨论】:
-
有一个 camlp4 预处理器,它使用新指令
deriving扩展了 ocaml 语法,除其他外,您可以指示是否希望为您机械地编写字符串转换函数。让人想起 Haskell 的派生 (deriving show) 的语法。 -
图书馆是there。虽然我从未使用过它,但我知道它非常好。我不确定它是否仍可用于 4.0+ 版本的 Ocaml。 (其中之一)作者有一个关于camlp4的优秀教程,one chapter描述了如何开发这样的扩展。
-
哦,可能和Core里面发现的一样,不知道。
-
谢谢。它似乎与 Core 中所做的类似。基本上,您可以在类型定义之后添加“with sexp”,camlp4 会为您派生与 Sexp.t 之间的转换函数(有通用打印和解析函数)。
-
啊,对了,我现在想起来了:iirc
Sexp的目标是为 ocaml 提供符号表达式(我相信在 lisp 中),它们可以以人类可读的格式序列化。一个副作用是它可以方便地转换为字符串。