问题描述
什么是定义在球拍使用或的拍摄微距的最简单的方法?
What's the simplest way to define a capturing macro using define-syntax
or define-syntax-rule
in Racket?
作为具体的例子,这里的琐碎在CL式宏系统.
As a concrete example, here's the trivial aif
in a CL-style macro system.
(defmacro aif (test if-true &optional if-false)
`(let ((it ,test))
(if it ,if-true ,if-false)))
的想法是,将被绑定到的在和子句的结果.天真的音译(减去可选的替代项)是
The idea is that it
will be bound to the result of test
in the if-true
and if-false
clauses. The naive transliteration (minus optional alternative) is
(define-syntax-rule (aif test if-true if-false)
(let ((it test))
(if it if-true if-false)))
如果您尝试使用中的所有条款,其评价毫无怨言,但错误:
which evaluates without complaint, but errors if you try to use it
in the clauses:
> (aif "Something" (displayln it) (displayln "Nope")))
reference to undefined identifier: it
anaphora
egg 将aif
实现为
(define-syntax aif
(ir-macro-transformer
(lambda (form inject compare?)
(let ((it (inject 'it)))
(let ((test (cadr form))
(consequent (caddr form))
(alternative (cdddr form)))
(if (null? alternative)
`(let ((,it ,test))
(if ,it ,consequent))
`(let ((,it ,test))
(if ,it ,consequent ,(car alternative)))))))))
但球拍似乎不具有定义或记录.
but Racket doesn't seem to have ir-macro-transformer
defined or documented.
推荐答案
球拍宏被设计为默认避免捕获.当您使用define-syntax-rule
时,它将遵循词汇范围.
Racket macros are designed to avoid capture by default. When you use define-syntax-rule
it will respect lexical scope.
当您要故意破坏卫生"时,传统上在Scheme中,您必须使用syntax-case
,并且(请谨慎地)使用datum->syntax
.
When you want to "break hygiene" intentionally, traditionally in Scheme you have to use syntax-case
and (carefully) use datum->syntax
.
但在球拍做照应"宏最简单,最安全的方法是使用语法参数和简单
But in Racket the easiest and safest way to do "anaphoric" macros is with a syntax parameter and the simple define-syntax-rule
.
例如:
(require racket/stxparam)
(define-syntax-parameter it
(lambda (stx)
(raise-syntax-error (syntax-e stx) "can only be used inside aif")))
(define-syntax-rule (aif condition true-expr false-expr)
(let ([tmp condition])
(if tmp
(syntax-parameterize ([it (make-rename-transformer #'tmp)])
true-expr)
false-expr)))
我写了一篇关于语法参数这里,你也应该阅读礼Barzilay的 肮脏的卫生学博客文章一>和 清洁与语法参数纸(PDF)保持它
I wrote about syntax parameters here and also you should read Eli Barzilay's Dirty Looking Hygiene blog post and Keeping it Clean with Syntax Parameters paper (PDF).
这篇关于捕获宏方案的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!