lisp函数可以返回引用还是通过引用接收参数?

lisp函数可以返回引用还是通过引用接收参数?,lisp,reference,Lisp,Reference,我想知道这是如何工作的: (setf(车辆x)42) (car x)是否返回对setf的可分配引用?还是仅仅是宏观魔术?setf或car是如何工作的 我知道在函数式编程中,通过引用进行传递是一种可怕的罪恶,但我想知道上面是如何做到的。在Common Lisp中,这是一个地方。位置是定义了setf扩展器的表单。它有点像一个广义的参考 要进行深入的治疗,请查看。这是一种宏魔法。表单(setf位置值)只是一个专门的宏扩展。例如,(setf(car x)42)将被翻译成如下内容:(rplaca x 42

我想知道这是如何工作的:

(setf(车辆x)42)

(car x)是否返回对setf的可分配引用?还是仅仅是宏观魔术?setf或car是如何工作的

我知道在函数式编程中,通过引用进行传递是一种可怕的罪恶,但我想知道上面是如何做到的。

在Common Lisp中,这是一个地方。位置是定义了setf扩展器的表单。它有点像一个广义的参考


要进行深入的治疗,请查看。

这是一种宏魔法。表单(setf位置值)只是一个专门的宏扩展。例如,(setf(car x)42)将被翻译成如下内容:(rplaca x 42)

您可以看到Lisp实现如何使用MACROEXPAND扩展SETF表单,如下所示(我的示例是使用SBCL,其他实现可能有完全不同的扩展):

您还可以定义自己的扩展:

CL-USER> (macroexpand '(setf (aref foo 10) 1234))
(SB-KERNEL:%ASET FOO 10 1234)
T
CL-USER> (defvar *value* 0)
*VALUE*
CL-USER> (defun get-value () *value*)
GET-VALUE
CL-USER> (defun (setf get-value) (x) (setq *value* x))
(SETF GET-VALUE)
CL-USER> (setf (get-value) 42)
42
CL-USER> (get-value)
42
CL-USER> (macroexpand '(setf (get-value) 23))
(LET* ()
  (MULTIPLE-VALUE-BIND (#:NEW1058) 23 (FUNCALL #'(SETF GET-VALUE) #:NEW1058)))
T