如何在相互递归类型中使用派生Show() ?



我们直接看代码。

type symbol =
| JumpDes of int 
| CallDes of func
| StarDes of exp (*here needs the definition of type exp*)
deriving (Show)
type exp =
| Const of const
| Symbol of symbol (*here needs the definition of type symbol*)
| Reg of reg
| Assist of assistop
| Ptr of ptraddr
| Label of string
deriving (Show)

我想使用包派生来打印关于这两种类型的信息。根据它的文档,我只需要在我想打印的类型后面加上deriving (Show)。但是我不能通过像这样添加and来定义相互递归类型:

type symbol =
| JumpDes of int
| CallDes of func
| StarDes of exp 
deriving (Show)
and exp = (*note that it's line 240*)
| Const of const
| Symbol of symbol
| Reg of reg
| Assist of assistop 
| Ptr of ptraddr
| Label of string
deriving (Show)

编译上面的代码会得到下面的错误:

File "type.ml", line 240, characters 16-17:
Parse error: [semi] expected after [str_item] (in [implem])
File "type.ml", line 1:
Error: Error while running external preprocessor

如果我想在相互递归类型上使用派生Show(),我该怎么做?谢谢你的帮助!

可以使用ppx_derived1派生出漂亮的打印函数。首先,确保你已经安装了

opam install ppx_deriving
接下来,让我们基于您的输入创建一个示例项目,
type func = string [@@deriving show]
type const = int [@@deriving show]
type reg = int [@@deriving show]
type assistop = int [@@deriving show]
type ptraddr = int [@@deriving show]
type symbol =
| JumpDes of int
| CallDes of func
| StarDes of exp
[@@deriving show]
and exp =
| Const of const
| Symbol of symbol
| Reg of reg
| Assist of assistop
| Ptr of ptraddr
| Label of string
[@@deriving show]

let () =
let input = StarDes (Const 1) in
Format.printf "%sn%a@n" (show_symbol input) pp_symbol input

我为你的问题中没有提供的类型添加了一些别名。注意,所有类型都必须指定[@@deriving show]。当类型是递归时,只需将and视为type。基本上,和你做的一样,但是我们需要使用ppx语法,例如,[@@deriving show],而不是Ocsigen的。

在程序的最后,有一个示例显示了如何使用生成的函数。有两种类型的函数,show_foofoo类型的值转换为字符串,而美观打印函数pp_foofoo打印到格式化程序中,由于不需要创建中间字符串,因此速度更快。打印机与%a说明符一起使用,并接受两个参数,打印机本身和要打印的值。所以不需要加括号,这也是一个小胜利。我在示例中使用了这两个选项,以便您可以对它们进行对比。

最后,如何构建它?如果您使用的是dune,那么下面是dune示例文件

(executable
(name example)
(preprocess
(pps ppx_deriving.show)))

您可以自己创建dune文件或使用以下命令(假设我们的程序在example.ml文件中),

dune init executable example --ppx=ppx_deriving.show

你可以用

dune exec ./example.exe

如果你使用ocamlbuild而不是dune,那么只需将-package ppx_deriving.show添加到ocamlbuild调用中,例如

ocamlbuild -package ppx_deriving.show example.native
./example.native

都将打印

(Example.StarDes (Example.Const 1))
(Example.StarDes (Example.Const 1))

如果您正在使用其他构建系统,请不要犹豫,我们将需要更多关于您的构建系统的信息或项目链接。如果你刚开始一个新项目,不知道应该使用哪个构建系统,那么dune就是答案。


1)这不是唯一的选择。您还可以使用ppx_jane的sexp派生程序ppx_show,可能还有更多。

相关内容

  • 没有找到相关文章

最新更新