1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215
|
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"
"http://www.w3.org/TR/REC-html40/loose.dtd">
<HTML>
<HEAD>
<META http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<META name="GENERATOR" content="hevea 1.06">
<TITLE>
OCaml syntax trees
</TITLE>
</HEAD>
<BODY TEXT=black BGCOLOR=white>
<A HREF="tutorial005.html"><IMG SRC ="previous_motif.gif" ALT="Previous"></A>
<A HREF="index.html"><IMG SRC ="contents_motif.gif" ALT="Up"></A>
<A HREF="tutorial007.html"><IMG SRC ="next_motif.gif" ALT="Next"></A>
<HR>
<TABLE CELLPADDING=0 CELLSPACING=0 WIDTH="100%">
<TR><TD BGCOLOR="#2de52d"><DIV ALIGN=center><TABLE>
<TR><TD><A NAME="htoc52"><B><FONT SIZE=6>Chapter 6</FONT></B></A></TD>
<TD WIDTH="100%" ALIGN=center><B><FONT SIZE=6>OCaml syntax trees</FONT></B></TD>
</TR></TABLE></DIV></TD>
</TR></TABLE>
<A NAME="c:tutast"></A>
This chapter explains how to create <CODE>OCaml</CODE> syntax trees using
quotations.<BR>
<BR>
The <CODE>OCaml</CODE> syntax tree is defined in the module
<CODE>MLast</CODE> (file ``mLast.mli''): it is of course always possible to create
your syntax tree nodes by combining values of these types. But, for
that, you need a precise documentation of all the constructors, how
they have to be used, and which syntactic construct they correspond
to.<BR>
<BR>
Chapter <A HREF="tutorial004.html#c:tutquot">4</A> explained us that quotations are helpful to
represent abstract values with concrete syntax. This is very adapted
for abstract syntax trees, since they have corresponding concrete
syntaxes. In this case, you have nothing to learn: if you know the
concrete syntax, you know the abstract syntax. Actually, you need to
know the revised syntax (chapter <A HREF="tutorial005.html#c:tutrevis">5</A>) because it is the
syntax used in these quotations.<BR>
<BR>
The provided quotation extension is the file <CODE>q_MLast.cmo</CODE>. Once
this file loaded, you can write any complicated piece of program in
concrete syntax, e.g.:
<PRE>
<:expr< match f $x$ with [ $uid:p$ -> $x$ | C z -> 7 ] >>
</PRE>This example corresponds exactly to this code (written in normal syntax):
<PRE>
MLast.ExMat
(loc, MLast.ExApp (loc, MLast.ExLid (loc, "f"), x),
[MLast.PaUid (loc, p), None, x;
MLast.PaApp
(loc, MLast.PaUid (loc, "C"), MLast.PaLid (loc, "z")), None,
MLast.ExInt (loc, "7")]);;
</PRE>
These two forms are absolutely equivalent, but the first one is much
simpler and more readable. Notice the expressions between dollar signs
<CODE>$</CODE>: they are antiquotations (see chapter
<A HREF="tutorial004.html#c:tutquot">4</A>). We are going to see how to use them.<BR>
<BR>
For the moment, here is the list of the quotations defined in the file
<CODE>q_MLast.cmo</CODE>:
<UL><LI><CODE>expr</CODE> to create expression nodes<BR>
<BR>
<LI><CODE>patt</CODE> to create pattern nodes<BR>
<BR>
<LI><CODE>ctyp</CODE> to create type nodes<BR>
<BR>
<LI><CODE>sig_item</CODE> to create signature item nodes<BR>
<BR>
<LI><CODE>str_item</CODE> to create structure item nodes<BR>
<BR>
<LI><CODE>module_type</CODE> to create module type nodes<BR>
<BR>
<LI><CODE>module_expr</CODE> to create module expression nodes</UL>
Each of these quotations use the revised syntax (chapter
<A HREF="tutorial005.html#c:tutrevis">5</A>). You have to know that their expression form
(i.e. not pattern) all contain the variable named <CODE>"loc"</CODE>.
It allows you to specify a source location to the syntax tree.
There must then exist a variable <CODE>"loc"</CODE> visible in the
environment where the quotation is used.<BR>
<BR>
Notice that in the <CODE>Camlp4</CODE> grammar system (chapter
<A HREF="tutorial003.html#c:tutgram">3</A>), the variable <CODE>"loc"</CODE> in defined in all semantic
actions of the rules: Camlp4 grammar system and Camlp4 quotations of
abstract syntax trees are made to work together.<BR>
<BR>
<A NAME="toc45"></A><TABLE CELLPADDING=0 CELLSPACING=0 WIDTH="100%">
<TR><TD BGCOLOR="#66ff66"><DIV ALIGN=center><TABLE>
<TR><TD><A NAME="htoc53"><B><FONT SIZE=5>6.1</FONT></B></A></TD>
<TD WIDTH="100%" ALIGN=center><B><FONT SIZE=5>Antiquotations</FONT></B></TD>
</TR></TABLE></DIV></TD>
</TR></TABLE><BR>
The antiquotations allow to insert abstract syntax trees inside other
abstract syntax trees. They are enclosed by dollar signs
<CODE>$</CODE>. Between these dollars, you can put any expression or pattern
in the enclosing syntax.<BR>
<BR>
For example, if you have a variable <CODE>"x"</CODE> of type
<CODE>MLast.expr</CODE>, you may want to create ``the tree node
corresponding to the call of some function <CODE>"f"</CODE> with this
expression. This can be written:
<PRE>
<:expr< f $x$ >>
</PRE>
Note that if the quotation is is position of pattern, the content of
the quotation must be a pattern: here are legal pieces of program (in
normal syntax):
<PRE>
function <:expr< f $x$ >> -> x;;
function <:expr< f $_$ >> -> 1;;
</PRE>
<A NAME="toc46"></A><TABLE CELLPADDING=0 CELLSPACING=0 WIDTH="100%">
<TR><TD BGCOLOR="#66ff66"><DIV ALIGN=center><TABLE>
<TR><TD><A NAME="htoc54"><B><FONT SIZE=5>6.2</FONT></B></A></TD>
<TD WIDTH="100%" ALIGN=center><B><FONT SIZE=5>Antiquotations labels</FONT></B></TD>
</TR></TABLE></DIV></TD>
</TR></TABLE><BR>
Some of these antiquotations may be used with a label (an identifier
ending with a colon character <CODE>":"</CODE> in the beginning of the
antiquotation). It is for the case when the concrete syntax is not
enough to know what we are talking about.<BR>
<BR>
For example, if <CODE>x</CODE> is a variable of type string, we need ways
to create 1/ the tree node corresponding to the variable whose name is
the value of <CODE>x</CODE> 2/ the tree node corresponding to the string
whose content is the value of <CODE>x</CODE> 3/ the tree node
corresponding to the constructor whose name is the value of
<CODE>x</CODE>.<BR>
<BR>
Labels allow to do that: in the first case, it must be <CODE>"lid"</CODE>
(for ``l(owercase) id(entifier)''), in the second case, <CODE>"str"</CODE>
(for ``str(ing)''), in the third case, <CODE>"uid"</CODE> (for ``u(ppercase)
id(entifier)''), i.e. respectively:
<PRE>
<:expr< f $lid:x$ >>
<:expr< f $str:x$ >>
<:expr< f $uid:x$ >>
</PRE>Therefore:
<PRE>
let x = "foo" in <:expr< f $lid:x$ >> is equivalent to: <:expr< f foo >>
let x = "foo" in <:expr< f $str:x$ >> " <:expr< f "foo" >>
let x = "Foo" in <:expr< f $uid:x$ >> " <:expr< f Foo >>
</PRE>
<B>Important remark</B>: the antiquotations of type string (str) and
character (chr) must contain an ``escaped'' string: some characters
like backslashes, quotes, doubles quotes must be prefixed by a
backslash. To be sure, use the OCaml library functions
<CODE>"String.Escaped"</CODE> and <CODE>"Char.Escaped"</CODE>.<BR>
<BR>
A label often encountered is <CODE>"list"</CODE>: it is when the syntactic
construct may expect a list at this place. Here are examples with
two antiquotations, one being labelled, the other not:
<PRE>
<:expr< [| $list:x$ |] >>
<:expr< [| $x$ |] >>
</PRE><UL><LI>
In the first case, <CODE>x</CODE> must be a value of type
<CODE>MLast.expr</CODE> list, and the quotation represents an array whose
elements are in <CODE>x</CODE>.
<LI>In the second case, <CODE>x</CODE> if of type <CODE>MLast.expr</CODE>, and the
quotation represents an array of just one element.
</UL>
Notice that the antiquotations must respect the enclosing syntax
rules: if <CODE>x</CODE> and <CODE>y</CODE> are of type <CODE>MLast.expr</CODE> and
<CODE>z</CODE> of type <CODE>MLast.expr</CODE> list, the code:
<PRE>
<:expr< [| $list: x::y::z $ |] >>
</PRE>is correct in normal syntax, but if you use the revised syntax, you must
write it:
<PRE>
<:expr< [| $list: [x; y :: z] $ |] >>
</PRE>
<A NAME="toc47"></A><TABLE CELLPADDING=0 CELLSPACING=0 WIDTH="100%">
<TR><TD BGCOLOR="#66ff66"><DIV ALIGN=center><TABLE>
<TR><TD><A NAME="htoc55"><B><FONT SIZE=5>6.3</FONT></B></A></TD>
<TD WIDTH="100%" ALIGN=center><B><FONT SIZE=5>Description</FONT></B></TD>
</TR></TABLE></DIV></TD>
</TR></TABLE><BR>
Well, we could describe all nodes one by one, but they are actually
already described in the reference manual. Refer to it.
<BR>
<BR>
<I><FONT COLOR=maroon>
<br>
For remarks about Camlp4, write to:
<img src="http://cristal.inria.fr/~ddr/images/email.jpg" alt=email align=top>
</FONT></I><HR>
<A HREF="tutorial005.html"><IMG SRC ="previous_motif.gif" ALT="Previous"></A>
<A HREF="index.html"><IMG SRC ="contents_motif.gif" ALT="Up"></A>
<A HREF="tutorial007.html"><IMG SRC ="next_motif.gif" ALT="Next"></A>
</BODY>
</HTML>
|