2013-03-31 2 views
5

У меня есть этот кусок кода, который содержит цитату camlp4.Печать OCaml AST как OCaml Код

let f_name = "my_func" 
<:str_item< value $lid:f_name$ a = a * 2 >> 

После запуска этого через camlp4of, он производит это:

Ast.StExp (_loc, 
    (Ast.ExApp (_loc, 
     (Ast.ExApp (_loc, (Ast.ExId (_loc, (Ast.IdLid (_loc, "=")))), 
      (Ast.ExApp (_loc, 
      (Ast.ExApp (_loc, 
       (Ast.ExId (_loc, (Ast.IdLid (_loc, "value")))), 
       (Ast.ExId (_loc, (Ast.IdLid (_loc, f_name)))))), 
      (Ast.ExId (_loc, (Ast.IdLid (_loc, "a")))))))), 
     (Ast.ExApp (_loc, 
      (Ast.ExApp (_loc, (Ast.ExId (_loc, (Ast.IdLid (_loc, "*")))), 
      (Ast.ExId (_loc, (Ast.IdLid (_loc, "a")))))), 
      (Ast.ExInt (_loc, "2"))))))) 

Мой вопрос заключается в следующем, есть в любом случае, чтобы распечатать сгенерированный код OCaml? Какую команду camlp4of или параметр следует использовать для показа кода? То, что я ожидаю увидеть из приведенного выше примера, следующее:

value my_func a = a * 2 

Возможно ли это? Причина в том, что я хочу сделать некоторую отладку, чтобы посмотреть, как выглядит сгенерированный код ocaml.

ответ

5

Это хороший вопрос, который я задал себе несколько дней назад.

Вы можете использовать `Camlp4.PreCast.Printers.OCaml.print_implem, который имеет тип

value print_implem : ?input_file:string -> ?output_file:string -> 
        Ast.str_item -> unit; 

Например, в верхнем уровне (только с выходом последней команды показан):

# #use "topfind";; 
# #require "camlp4";; 
# #load "camlp4of.cma";; 
# open Camlp4.PreCast;; 
# let _loc = Loc.ghost;; 
# let test = 
    let f_name = "my_func" in 
    <:str_item< value $lid:f_name$ a = a * 2 >>;; 
# Printers.OCaml.print_implem test;; 
let _ = (value my_func a) = (a * 2);; 
- : unit =() 

Другим решением является создание расширения синтаксиса, которое будет производить вывод, который вы ищете. Например, Camlp4AstFilter, который просто проигнорировал бы его вход, и вернул бы ваш материал в качестве вывода, так что вы можете использовать camlp4of my_filter.cmo -str '', чтобы получить AST, который вы ищете.

+0

Функция 'Camlp4.PreCast.Printers.OCaml.print_implem' работает только с' str_item'. Есть ли другие принтеры, которые могут печатать 'expr'? –

+1

Под крюком, конечно, но они не отображаются через интерфейс «Принтеры». Как насчет того, чтобы обернуть ваше выражение как 'let _ = ' str_item? Для типов вы также можете использовать 'type foo = ' и т. Д. – gasche

Смежные вопросы