An explicitly implicitly renaming macro transformer.
Ok, so this is define-er-syntax*
. Pretty much the closest thing
we’ve got to the Common Lisp, Emacs Lisp style defmacros.
You explicitly make for renaming things that you don’t want to clobber into the environment. The equivalent of renaming with gensyms in those other languages. Here’s an implementation of anaphoric if:
(define-er-syntax*
(e-aif test yeah naw)
`(,(rename 'let) ((it ,test)) (,(rename 'if) it ,yeah ,naw)))
(e-aif (+ 2 2) (+ 2 it) 5)
⇒ 6
But unlike defmacro, and like syntax-rules, you can have several patterns to dispatch between. (It uses matchable.)
(define-er-syntax*
((foo bar) `(,(rename 'quote) ,bar))
((foo baz quux) `(,(rename 'quote) (,baz ,quux))))
(foo beer)
⇒ beer
(foo orange soda)
⇒ (orange soda)
If you’re getting tired of all that renaming, there’s ir
and
except
in addition to rename
and compare
:
(define-er-syntax*
(ei-aif test yeah naw)
(ir `(let ((,(except 'it) ,(except test)))
(if ,(except 'it) ,(except yeah) ,(except naw)))))
(ei-aif (+ 4 4) it 9)
Of course, if you only want ir all the time, let me introduce you to
my friend, define-ir-syntax*
from brev-separate:
(import brev-separate)
(define-ir-syntax*
(i-aif test yeah naw)
`(let ((,(inject 'it) ,test)) (if ,(inject 'it) ,yeah ,naw)))
(i-aif (* 9 9) (+ 1 it) 18)
⇒ 82
99% of the time, that’s what you want to use instead of this egg and
define-er-syntax*
.
define-ir-syntax*
is even better since you don’t have to “except”
the macro’s own inputs, you only have to “inject” things you really
want to inject there, like anaphora and generated defines.
But define-er-syntax*
exists for that 1% of times when you’re
building a macro that’s really weird and complicated and you need full
control over your renaming since you might be loading and reloading
generated code or other shenanigans.
TL;DR: don’t use define-er-syntax*
unless you know what you’re
doing; use syntax-rules
if you don’t need to inject and
define-ir-syntax*
if you do.
What am I doing with my life… making code to generate code to generate code to generate code to generate code to…
For source code,
git clone https://idiomdrottning.org/define-er-syntax