Macros symbol macrolet如何处理let阴影?

Macros symbol macrolet如何处理let阴影?,macros,common-lisp,Macros,Common Lisp,从 symbol macrolet在词汇上为符号命名的每个符号宏建立扩展函数 符号宏let的使用可以被let隐藏 这允许以下代码工作(内部*b*x绑定到“1”): 我的问题是:symbol宏如何让我们知道哪些形式可以对其进行阴影处理?我要求宏不能保证let没有被重新定义,或者用户没有创建另一个表单来完成与let相同的工作。这是一个特殊的“哑巴”案例,只寻找cl:let符号吗?还是有更先进的技术在进行 如果这个问题太模糊,我很乐意编辑它,因为我很难清楚地表达这个问题。参见3.1.1.4和相关资料

symbol macrolet在词汇上为符号命名的每个符号宏建立扩展函数

符号宏let的使用可以被let隐藏

这允许以下代码工作(内部*b*x绑定到“1”):

我的问题是:symbol宏如何让我们知道哪些形式可以对其进行阴影处理?我要求宏不能保证let没有被重新定义,或者用户没有创建另一个表单来完成与let相同的工作。这是一个特殊的“哑巴”案例,只寻找cl:let符号吗?还是有更先进的技术在进行


如果这个问题太模糊,我很乐意编辑它,因为我很难清楚地表达这个问题。

参见3.1.1.4和相关资料

那句话是从哪里来的?我不认为这是完全正确的,因为let不是唯一可以在词汇环境中隐藏由macrolet建立的名称的东西

我认为揭示词汇环境不仅仅是一个抽象的概念并没有多大坏处,而是有一个实际的数据结构来体现它。通过&environment绑定机制,宏在编译时可以使用词汇环境。宏可以使用它来获得一个进入环境的窗口,并且有一个使用环境的协议。因此,举一个简单的例子,可以编写对词法环境中的声明敏感的宏,例如,如果变量声明为fixnum,则可以进行单向扩展

环境的实现由实现者来完成,但它只是包含名称信息的名称堆栈。因此,lambda绑定、macrolet、labels、let*等只是将新名称推入堆栈,从而隐藏旧名称。词法声明增加了有关名称的信息

然后,编译器或计算器使用环境(堆栈)来指导生成的代码或执行行为。值得注意的是,这种数据结构不需要存在到运行时,尽管它的一些后代通常会帮助调试器


所以要回答您的问题:macrolet不知道它的&body中的表单可能在做什么。

正如您所看到的,SYMBOL-macrolet是Common Lisp的内置功能。就让我来吧。这些特殊运算符不能重新定义,也不允许这样做

Common Lisp只有一组固定的特殊运算符,用户无法定义一组特殊运算符。仅定义了以下内容:


由于宏将被扩展,它们将扩展到基本原语:函数调用和特殊形式。因此,编译器/解释器实现符号宏,并且此任务受基元形式数量的限制。如果用户实现他/她自己的LET,最终这个实现也归结为函数调用和特殊形式——宏的所有用途最终都会扩展到这些。但是这些都是已知的,对于symbol macrolet来说也没有什么新的东西。

我确实不确定你到底在问什么,但是请记住,
symbol macrolet
let
本身都是特殊的操作符——语言的基石。他们不应该被重新定义或阴影,否则混乱将会接踵而至。是的,我想知道let is special这个事实是否与这是如何做到的有关。看了Ben的答案后,我了解到宏可以获得有关它们所在词汇环境的信息,这些信息非常有趣,可能相关……我需要阅读!引用的文本来自我在问题顶部链接的hyperspec页面,但示例代码是我的。不过我对环境一无所知,非常感谢,不知道我是怎么错过的,但我真的需要读一读!
CT> (with-slots (x y z) *b* 
      (let ((x 10))
        (format nil "~a ~a ~a" x y z)))
"10 2 3"