Tia*_*ong 3 dynamic common-lisp exit
根据Common Lisp the Language的动态非本地退出部分,第2版,
一旦启动控制权转移,就会放弃干预出口; 在抛出的情况下,这发生在实施说明中提到的"第二次通过"的开始.尝试将控制权转移到动态范围已结束的出口是错误的.
1.3.4但是在SBCL 中:
(catch 'a
(catch 'b
(unwind-protect
(throw 'a "returning from protected")
(throw 'b "returning from unwind"))))
;; => "returning from unwind"
Run Code Online (Sandbox Code Playgroud)
这似乎不正确.'b在执行受保护和清理表格之间是否应该解除退出点,从而使上述违法?同一页上的划船示例表明了相同的情况.
相反,SBCL的行为似乎与替代提案相对应:
...放弃退出应该与
unwind-protect清理条款的评估以及动态绑定和捕获标记的撤消混为一谈,以相反的顺序执行所有操作.
这只是CLtL2与最终规格不同的问题吗?
正如jkiiski所解释的那样,ANSI Common Lisp中的行为未定义.UNWIND-PROTECTCLHS部分引用了这个例子:
;;; The following has undefined consequences because the catch of B is
;;; passed over by the first THROW, hence portable programs must assume
;;; its dynamic extent is terminated. The binding of the catch tag is not
;;; yet disestablished and therefore it is the target of the second throw.
(catch 'a
(catch 'b
(unwind-protect (throw 'a 1)
(throw 'b 2))))
Run Code Online (Sandbox Code Playgroud)