diff options
author | simonpj@microsoft.com <unknown> | 2009-09-10 12:58:48 +0000 |
---|---|---|
committer | simonpj@microsoft.com <unknown> | 2009-09-10 12:58:48 +0000 |
commit | 1e436f2bb208a6c990743afaf17b7c2a93c31742 (patch) | |
tree | 24a886219949e5b7049db2250d15cf0672c6a5b7 /docs | |
parent | c281c07544cc58afe68fdda96afe53ba46985732 (diff) | |
download | haskell-1e436f2bb208a6c990743afaf17b7c2a93c31742.tar.gz |
Three improvements to Template Haskell (fixes #3467)
This patch implements three significant improvements to Template Haskell.
Declaration-level splices with no "$"
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
This change simply allows you to omit the "$(...)" wrapper for
declaration-level TH splices. An expression all by itself is
not legal, so we now treat it as a TH splice. Thus you can now
say
data T = T1 | T2
deriveMyStuff ''T
where deriveMyStuff :: Name -> Q [Dec]
This makes a much nicer interface for clients of libraries that use
TH: no scary $(deriveMyStuff ''T).
Nested top-level splices
~~~~~~~~~~~~~~~~~~~~~~~~
Previously TH would reject this, saying that splices cannot be nested:
f x = $(g $(h 'x))
But there is no reason for this not to work. First $(h 'x) is run,
yielding code <blah> that is spliced instead of the $(h 'x). Then (g
<blah>) is typechecked and run, yielding code that replaces the
$(g ...) splice.
So this simply lifts the restriction.
Fix Trac #3467: non-top-level type splices
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
It appears that when I added the ability to splice types in TH
programs, I failed to pay attention to non-top-level splices -- that
is, splices inside quotatation brackets.
This patch fixes the problem. I had to modify HsType, so there's a
knock-on change to Haddock.
Its seems that a lot of lines of code has changed, but almost all the
new lines are comments!
General tidying up
~~~~~~~~~~~~~~~~~~
As a result of thinking all this out I re-jigged the data type ThStage,
which had far too many values before. And I wrote a nice state transition
diagram to make it all precise;
see Note [Template Haskell state diagram] in TcSplice
Lots more refactoring in TcSplice, resulting in significantly less code.
(A few more lines, but actually less code -- the rest is comments.)
I think the result is significantly cleaner.
Diffstat (limited to 'docs')
-rw-r--r-- | docs/users_guide/glasgow_exts.xml | 28 |
1 files changed, 23 insertions, 5 deletions
diff --git a/docs/users_guide/glasgow_exts.xml b/docs/users_guide/glasgow_exts.xml index bf2e9ace80..fb21918e25 100644 --- a/docs/users_guide/glasgow_exts.xml +++ b/docs/users_guide/glasgow_exts.xml @@ -6065,12 +6065,11 @@ Wiki page</ulink>. have type <literal>Q Exp</literal></para></listitem> <listitem><para> an type; the spliced expression must have type <literal>Q Typ</literal></para></listitem> - <listitem><para> a list of top-level declarations; the spliced expression must have type <literal>Q [Dec]</literal></para></listitem> + <listitem><para> a list of top-level declarations; the spliced expression + must have type <literal>Q [Dec]</literal></para></listitem> </itemizedlist> - </para> Inside a splice you can can only call functions defined in imported modules, - not functions defined elsewhere in the same module.</listitem> - + not functions defined elsewhere in the same module.</para></listitem> <listitem><para> A expression quotation is written in Oxford brackets, thus: @@ -6087,7 +6086,7 @@ Wiki page</ulink>. A quasi-quotation can appear in either a pattern context or an expression context and is also written in Oxford brackets: <itemizedlist> - <listitem><para> <literal>[:<replaceable>varid</replaceable>| ... |]</literal>, + <listitem><para> <literal>[$<replaceable>varid</replaceable>| ... |]</literal>, where the "..." is an arbitrary string; a full description of the quasi-quotation facility is given in <xref linkend="th-quasiquotation"/>.</para></listitem> </itemizedlist></para></listitem> @@ -6108,6 +6107,25 @@ Wiki page</ulink>. </para> </listitem> + <listitem><para> You may omit the <literal>$(...)</literal> in a top-level declaration splice. + Simply writing an expression (rather than a declaration) implies a splice. For example, you can write +<programlisting> +module Foo where +import Bar + +f x = x + +$(deriveStuff 'f) -- Uses the $(...) notation + +g y = y+1 + +deriveStuff 'g -- Omits the $(...) + +h z = z-1 +</programlisting> + This abbreviation makes top-level declaration slices quieter and less intimidating. + </para></listitem> + </itemizedlist> (Compared to the original paper, there are many differences of detail. |