这两个Scheme宏之间有什么区别?

huangapple go评论56阅读模式
英文:

What is the difference between the these two scheme macros?

问题

提供的是使用 mit-scheme 的代码。

唯一的修改是从 (cthen (make-syntactic-closure env '(it) (third exp))) 改成了 (cthen (third exp))

简而言之,make-syntactic-closure 有什么不同之处?

我尝试了这两个宏的版本,但得到了相同的结果。

英文:

provided using mit-scheme

The only modification is from (cthen (make-syntactic-closure env '(it) (third exp))) to (cthen (third exp))

In brief, what difference does make-syntactic-closure make?

(define-syntax aif
  (sc-macro-transformer
   (lambda (exp env)
     (let ((test (make-syntactic-closure env '(it) (second exp)))
	   (cthen (make-syntactic-closure env '(it) (third exp)))
	   (celse (if (pair? (cdddr exp))
		      (make-syntactic-closure env '(it) (fourth exp))
		      #f)))
       `(let ((it ,test))
	  (if it ,cthen ,celse))))))


(let ((i 4))
  (aif (memv i '(2 4 6 8))
       (car it)))
(define-syntax aif
  (sc-macro-transformer
   (lambda (exp env)
     (let ((test (make-syntactic-closure env '(it) (second exp)))
           (cthen (third exp))
	   (celse (if (pair? (cdddr exp))
		      (make-syntactic-closure env '(it) (fourth exp))
		      #f)))
       `(let ((it ,test))
	  (if it ,cthen ,celse))))))


(let ((i 4))
  (aif (memv i '(2 4 6 8))
       (car it)))

I tried the two version of macro, but got the same result.

答案1

得分: 1

一个语法闭包捕获了语法环境,允许其中的标识符被用作变量的形式,而不是由宏变换器的环境提供的含义(它还允许您指定一个自由名称的列表,就像在这种情况下的 it,它可以在宏体中设置或以其他方式使用,并且在扩展的形式中使用该绑定;基本上它会从给定的环境中删除这些名称)

一个例子:

(let ((i 4)
      (x '(a b c)))
  (aif (memv i '(2 4 6 8))
       (car x)))

使用您的 aif 宏的第一个版本,这将评估为 'a。而使用第二个版本,它将生成一个错误 未绑定的变量:x,因为在宏中 cthen 是一个列表,而不是语法闭包,而且在宏变换器中未绑定 x,所以在评估扩展的主体时找不到它。

英文:

A syntactic closure captures the syntactic environment and allows identifiers present in it to be used in the form as variables, instead of having a meaning provided by the environment of the macro transformer (It also lets you specify a list of free names like it in this case that can be set or otherwise used in the macro body and have that binding used in the expanded form; basically it removes those names from the given environment)

An example:

(let ((i 4)
      (x '(a b c)))
  (aif (memv i '(2 4 6 8))
       (car x)))

With the first version of your aif macro, this evaluates to 'a. With the second version, it generates an error Unbound variable: x, because in the macro cthen is a list, not a syntactic closure, and x is unbound in the macro transformer so it can't be found when the expanded body is evaluated.

huangapple
  • 本文由 发表于 2023年1月8日 22:37:25
  • 转载请务必保留本文链接:https://go.coder-hub.com/75048613.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定