2015-12-31 11 views
5

Sto cercando di saperne di più su OCaml Extension Points e sto riscontrando problemi nel seguire la rappresentazione dei tipi di record nell'AST.Rappresentazione del tipo di record AST OCaml

sto rubando l'esempio qui sotto da questo post del blog:

http://whitequark.org/blog/2014/04/16/a-guide-to-extension-points-in-ocaml/

Utilizzando il file sorgente (foo.ml):

let _ = [%getenv "USER"] 

e di uscita del ocamlc -dparsetree fool.ml :

[ 
    structure_item (test.ml[1,0+0]..[1,0+24]) 
    Pstr_eval 
    expression (test.ml[1,0+8]..[1,0+24]) 
     Pexp_extension "getenv" 
     [ 
      structure_item (test.ml[1,0+17]..[1,0+23]) 
      Pstr_eval 
      expression (test.ml[1,0+17]..[1,0+23]) 
       Pexp_constant Const_string("USER",None) 
     ] 
    ] 

Da asttypes.mli e parsetree.mli posso seguire l'analisi albero pattern matching della linea

Pexp_constant Const_string("USER",None) 

Tuttavia, non posso più seguire ciò che accade quando l'albero sintattico rappresenta tipi di record. Sembra che i campi dei record non siano rappresentati nello stesso ordine in cui appaiono nella definizione del tipo e non tutti i campi sono obbligatori (o mostrati) nell'albero di analisi.

Da parsetree.mli:

type expression = { 
    pexp_desc: expression_desc; 
    pexp_loc: Location.t; 
    pexp_attributes: attributes; 
} 

L'uscita albero di analisi sembra solo per mostrare la posizione e il carico utile, ma sono probabilmente leggendo questo in modo non corretto.

Come si legge correttamente l'AST per i tipi di record? Per tipo espressione dovrebbe essere:

(* record type declaration and pexp_loc field *) 
expression (test.ml[1,0+8]..[1,0+24]) 
    (* pexp_desc field *) 
    Pexp_extension "getenv" 
    [ 
     ... 
    ] 
+1

Non sono sicuro di aver capito la tua domanda. pexp_desc è la descrizione effettiva dell'AST (è un tipo di somma grande). -dsourcetree è solo una rappresentazione schematica, non il valore OCaml effettivo dell'AST. – Drup

risposta

2

Sembra che manchi gli strumenti essenziali per studiare gli AST e utilizzare i punti di estensione. Questi strumenti sono il ppx_tools scritto da Alain Frisch. Uno di questi strumenti è stato progettato proprio per esplorare la rappresentazione concreta di AST, il suo nome è . Diciamo applicarlo al seguente file ast_record.mli:

type card = { 
    name: string; 
    address: string; 
    age: int; 
} 

L'uscita è

ocamlfind ppx_tools/dumpast ast_record.mli   
ast_record.mli 
==> 
[{psig_desc = 
    Psig_type 
    [{ptype_name = {txt = "card"}; ptype_params = []; ptype_cstrs = []; 
     ptype_kind = 
     Ptype_record 
     [{pld_name = {txt = "name"}; pld_mutable = Immutable; 
      pld_type = {ptyp_desc = Ptyp_constr ({txt = Lident "string"}, [])}}; 
     {pld_name = {txt = "address"}; pld_mutable = Immutable; 
      pld_type = {ptyp_desc = Ptyp_constr ({txt = Lident "string"}, [])}}; 
     {pld_name = {txt = "age"}; pld_mutable = Immutable; 
      pld_type = {ptyp_desc = Ptyp_constr ({txt = Lident "int"}, [])}}]; 
     ptype_private = Public; ptype_manifest = None}]}] 
========= 

che conferma che l'ordine delle etichette discografiche è conservata.

Per inciso, vorrei suggerire di studiare il codice sorgente di queste ppx_tools e forse anche il ppx estensione fornito con LWT. Sono molto brevi e molto ben scritti e una fonte di ispirazione raccomandabile.