2013-03-31 41 views
5

Tôi có đoạn mã này có chứa báo giá camlp4.In OCaml AST dưới dạng Mã OCaml

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

Sau khi chạy này thông qua camlp4of, nó tạo ra này:

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"))))))) 

Câu hỏi của tôi là thế này, là có anyway để in mã ocaml tạo? Tôi nên sử dụng lệnh hoặc tùy chọn nào camlp4of để hiển thị mã? Những gì tôi mong đợi để xem từ ví dụ trên là:

value my_func a = a * 2 

Điều đó có thể? Lý do là vì tôi muốn thực hiện một số gỡ lỗi để xem mã ocaml được tạo ra trông như thế nào.

Trả lời

5

Đó là một câu hỏi hay mà tôi đã tự hỏi mình vài ngày trước.

Bạn có thể sử dụng `Camlp4.PreCast.Printers.OCaml.print_implem trong đó có các loại

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

Ví dụ, trong mục cấp đầu (chỉ với đầu ra của lệnh cuối cùng được hiển thị):

# #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 =() 

Một giải pháp khác là tạo một tiện ích mở rộng cú pháp sẽ tạo ra kết quả bạn đang tìm kiếm. Ví dụ, một Camlp4AstFilter mà sẽ chỉ bỏ qua đầu vào của nó, và trả lại công cụ của bạn như là đầu ra, vì vậy bạn có thể sử dụng camlp4of my_filter.cmo -str '' để có được AST bạn đang tìm kiếm.

+0

Chức năng 'Camlp4.PreCast.Printers.OCaml.print_implem' chỉ hoạt động trên' str_item'. Có bất kỳ máy in nào khác có thể in 'expr' không? –

+1

Theo móc, chắc chắn, nhưng chúng không được hiển thị thông qua giao diện 'Máy in'. Điều gì về chỉ gói biểu thức của bạn như là một 'let _ = ' str_item? Đối với các loại, bạn cũng có thể thực hiện 'loại foo = ', v.v. – gasche