defun宏在lisp中是如何实现的?
How is the defun macro implemented in lisp?
我想了解有关 lisp 宏的更多信息,我想创建 defun
宏的简单实现。
我也对 lisp 在所有实现中的源代码感兴趣。
您可以轻松检查您的特定 CL 实现方式,defun
由 运行
实现
(macroexpand '(defun add2 (x) (+ x 2)))
在 SBCL
上扩展为:
(PROGN
(EVAL-WHEN (:COMPILE-TOPLEVEL) (SB-C:%COMPILER-DEFUN 'ADD2 NIL T))
(SB-IMPL::%DEFUN 'ADD2
(SB-INT:NAMED-LAMBDA ADD2
(X)
(BLOCK ADD2 (+ X 2)))
(SB-C:SOURCE-LOCATION)))
T
要查看实现的特定源代码,我将使用(在 Emacs 上)M-.
键绑定,然后我将编写 defun
并按回车键。然后Emacs会获取到源码:
(sb!xc:defmacro defun (&environment env name lambda-list &body body)
#!+sb-doc
"Define a function at top level."
[...]
我不打算粘贴整个宏,因为它太长了。如果您不使用 Emacs,您可以尝试在存储库中搜索,因为大多数实现都是开源的。
顺便说一句 defun
并没有那么特别。您可以使用 setf
-inf a symbol-function
到 lambda 来实现其中的大部分内容。例如:
(setf (symbol-function 'ADD3) #'(lambda (x) (+ x 3)))
; => #<FUNCTION (LAMBDA (X)) {1006E94EBB}>
(add3 4)
; => 7
这是一个棘手的问题,因为 bootstrapping: defun
does a lot of things (iow, calls a lot of functions), but to define those functions one needs a working defun
. Thus there are three(3!) definitions of defun
in clisp/src/init.lisp: 在第
行
defun 的最基本定义可能是这样的:
(defmacro defun (fname lambda-list &rest body)
`(setf (fdefinition ',fname)
(lambda ,lambda-list
(block ,fname ,@body))))
其实这是CLISP中第一个defun
的定义(第228行),只是那个时候还没有defmacro
and no backquote ,所以实际代码看起来更丑陋。
另见 我在其中讨论 defun
的宏展开。
我想了解有关 lisp 宏的更多信息,我想创建 defun
宏的简单实现。
我也对 lisp 在所有实现中的源代码感兴趣。
您可以轻松检查您的特定 CL 实现方式,defun
由 运行
(macroexpand '(defun add2 (x) (+ x 2)))
在 SBCL
上扩展为:
(PROGN
(EVAL-WHEN (:COMPILE-TOPLEVEL) (SB-C:%COMPILER-DEFUN 'ADD2 NIL T))
(SB-IMPL::%DEFUN 'ADD2
(SB-INT:NAMED-LAMBDA ADD2
(X)
(BLOCK ADD2 (+ X 2)))
(SB-C:SOURCE-LOCATION)))
T
要查看实现的特定源代码,我将使用(在 Emacs 上)M-.
键绑定,然后我将编写 defun
并按回车键。然后Emacs会获取到源码:
(sb!xc:defmacro defun (&environment env name lambda-list &body body)
#!+sb-doc
"Define a function at top level."
[...]
我不打算粘贴整个宏,因为它太长了。如果您不使用 Emacs,您可以尝试在存储库中搜索,因为大多数实现都是开源的。
顺便说一句 defun
并没有那么特别。您可以使用 setf
-inf a symbol-function
到 lambda 来实现其中的大部分内容。例如:
(setf (symbol-function 'ADD3) #'(lambda (x) (+ x 3)))
; => #<FUNCTION (LAMBDA (X)) {1006E94EBB}>
(add3 4)
; => 7
这是一个棘手的问题,因为 bootstrapping: defun
does a lot of things (iow, calls a lot of functions), but to define those functions one needs a working defun
. Thus there are three(3!) definitions of defun
in clisp/src/init.lisp: 在第
defun 的最基本定义可能是这样的:
(defmacro defun (fname lambda-list &rest body)
`(setf (fdefinition ',fname)
(lambda ,lambda-list
(block ,fname ,@body))))
其实这是CLISP中第一个defun
的定义(第228行),只是那个时候还没有defmacro
and no backquote ,所以实际代码看起来更丑陋。
另见 defun
的宏展开。