Basic unit type:
λ> replTy "()"
() :: ()
Basic functions:
λ> replTy "(fn x x)"
(fn x x) :: b -> b
λ> replTy "((fn x ()) (fn x x))"
((fn x ()) (fn x x)) :: ()
λ> repl "((fn x x) (fn x x))"
((fn x x) (fn x x)) :: c -> c
(fn x x)
Statically typed:
λ> repl "(() (fn x x))"
-- *** Exception: Couldn't match expected type: ()
-- against type: (b -> b) -> e
Standard quotation:
λ> replTy "'()"
'() :: 'Symbol
λ> repl "'(foo bar)"
'(foo bar) :: 'Symbol
(foo bar)
Statically typed quotation:
λ> replTy "~()"
~() :: '()
All quotes have type 'a
. Normal symbolic Lisp style is 'Symbol
,
quoting anything else, e.g. for unit, is '()
. Also things have to be
in scope:
λ> repl "~a"
-- *** Exception: Not in scope: `a'
Quoted function:
λ> replTy "'(fn x x)"
'(fn x x) :: 'Symbol
Quoted function:
λ> replTy "~(fn x x)"
~(fn x x) :: '(b -> b)
Notice the type is '(b -> b)
.
There's an eval
function:
λ> replTy "eval"
eval :: 'a -> a
It accepts a quoted a
and returns the a
that it represents. It
won't accept anything not quoted:
λ> replTy "(eval ())"
-- *** Exception: Couldn't match expected type: 'a
-- against type: ()
If given a symbolic quoted expression, it will just return it as-is:
λ> repl "(eval '())"
(eval '()) :: Symbol
()
λ> repl "(eval '((fn x x) '()))"
(eval '((fn x x) '())) :: Symbol
((fn x x) ())
Given a well-typed quoted expression it will run the code:
λ> repl "(eval ~((fn x x) '()))"
(eval ~((fn x x) '())) :: 'Symbol
()
λ> repl "(eval ~((fn x x) ()))"
(eval ~((fn x x) ())) :: ()
()
That's a very hard problem you're tackling here. Lisps can usually write self-interpreters, but typed self-interpreters are very hard (the usual conjecture is they don't exist for usual type systems, as a consequence of Gödel's theorems).* Providing
eval
as a builtin is one of the ways out, but then it's less clear that you can achieve other metaprogramming tasks — writingeval
in the language is a kind of benchmark for its metaprogramming power.*Should you want to read academic papers on how to do it, see papers at PLDI '09 (https://www.uni-marburg.de/fb12/ps/research/tsr?set_language=en) and POPL '15 ("Self-Representation in Girard's System U", not yet publicly available).