我正在探索Common Lisp语法的一些可能性,并且我想在某些情况下提供:around
一种make-instance
返回任意值的方法。为简单起见,nil
当我不传递所需参数时,请设为。它有效,但是在调用let时无效:
(defclass foo ()
((bar :initarg := :initform '())))
(defmethod make-instance :around ((type (eql 'foo)) &key =)
(if (not =) nil (call-next-method)))
(print (make-instance 'foo)) ;; => NIL
(print (let ((x (make-instance 'foo))) x)) ;; => #<FOO {10037EEDF3}>
有人可以解释这种情况吗?为什么呢?SBCL是否会尝试变得聪明,或者实际上是一项标准工作?我知道我可以使用apply解决它:
(print (let ((x (apply #'make-instance (list 'foo)))) x)) ;; => NIL
但是我不想依靠这种解决方法。实际上,我可以为此使用常规函数,这没关系,但是我想了解为什么它会以这种方式工作以及是否可以禁用此行为。
看起来像是MAKE-INSTANCE
SBCL(-> CTOR)中的优化尝试和常量类名之一...
这似乎可行:
(defmethod make-instance :around ((class (eql (find-class 'foo)))
&rest initargs
&key =
&allow-other-keys)
(declare (ignorable initargs))
(if (not =) nil (call-next-method)))
但是向SBCL专家咨询或提交错误报告可能很有用...
谢谢,实际上
(class (eql (find-class 'foo)))
足以使其工作,但很高兴知道您在此处使用的其他内容。