Macros 宏表达式中的Lisp求值变量
我有以下功能(我是Lisp的初学者): 其中,我的commandsend和reply宏是由另一个程序员编写的宏。我无法修改它 我的commandsend和reply宏将命令(在本例中为cmd)发送到服务器进程(用另一种编程语言编写),然后等待其应答。 然后在宏中使用用户给定的“:代码的回复部分”处理答案。列表(ok result)是一种模式,在宏中,解构绑定解构并将答案的适当部分绑定到ok和result(ok只是一个标志)。在此之后,执行“:reply part”的其他用户给定行。(用于结果处理) 我想做以下工作: 1,向另一个进程发送类似的命令(这是确定的) 2、使用结果调用函数(如do something)并使用其他一些参数,这些参数是我的乐趣的实际参数(此部分失败…) 我该怎么做?我认为问题在于,在宏展开之前,a和b没有计算,当宏展开时,Lisp搜索本地a和b,但没有a或b。有没有办法评估a和b?(因此宏可以将它们视为具体的值) 这是宏def:(由另一个程序员编写) 请求id为的的Def:Macros 宏表达式中的Lisp求值变量,macros,lisp,elisp,common-lisp,clisp,Macros,Lisp,Elisp,Common Lisp,Clisp,我有以下功能(我是Lisp的初学者): 其中,我的commandsend和reply宏是由另一个程序员编写的宏。我无法修改它 我的commandsend和reply宏将命令(在本例中为cmd)发送到服务器进程(用另一种编程语言编写),然后等待其应答。 然后在宏中使用用户给定的“:代码的回复部分”处理答案。列表(ok result)是一种模式,在宏中,解构绑定解构并将答案的适当部分绑定到ok和result(ok只是一个标志)。在此之后,执行“:reply part”的其他用户给定行。(用于结果处理
(defmacro* with-request-id ((&rest vars) &body body)
"Send `getid' to the server, and call `body' once the response
with the new ID has arrived. By then, global variable `*request-id*'
is bound to the latest request ID."
`(progn
(when (not (server-is-running))
(error "Server isn't running!"))
(when *reqid-queue*
(error "Some internal error occured. Please, restart the program!"))
(lexical-let (,@(loop for var in vars
collect `(,var ,var)))
(setf *reqid-queue* (lambda ()
(unwind-protect
(progn ,@body)
(setf *reqid-queue* nil)))))
(get-id)))
以及从另一个进程获取id:
(defun get-id ()
(send-command-to-process 'getid))
根本不查看代码(抱歉--没时间)---
a
和b
由函数my fun
评估。所有函数都首先计算其参数——只有宏和特殊形式不一定计算其所有参数
但是那些a
和b
值并没有传递给宏——传递给宏的唯一内容是绑定到cmd
的未赋值sexp。您甚至不在函数中定义cmd
您需要做的是将a
和b
的值替换为cmd
sexp。您根本没有展示如何定义/构造cmd
。使用a
和b
的值构造它,您应该可以
要构造cmd
sexp,请记住可以使用反引号语法来简化操作,使用逗号语法来传递a
和b
的值。例如
(let((cmd`)(一些有趣的(表达式)(使用)),a和b)))
使用CMD的代码)
这假设您传递给宏的代码不需要变量
a
和b
,它只需要它们的值。当调用函数my fun
时,参数已经计算过,因此我不清楚您面临的问题是什么
我看到的唯一奇怪的事情是宏不卫生,因此如果您的参数被命名而不是a
和b
,例如status
或status args
,您将遇到麻烦,因为表达式
(do-something <a> <b> results)
(做点什么结果)
将在宏重复使用这些名称的上下文中编译。您最好也显示宏(或其演示版本),而不仅仅是试图描述它。我真的不知道这意味着什么:
发送命令,就像我(喜欢做某事)在我的乐趣(这没关系)
我同意@phils。尝试显示您迄今为止尝试过的内容--确切的代码。说出它发生了什么,以及您期望/希望发生什么。正如我在问题中提到的,我尝试使用“我的commandsend and reply宏”及其“:reply”部分来定义我自己的回调函数。在回调中,我需要使用一些变量(参见示例,比如我在dosomething中使用的fun变量“a”和“b”)。发生了什么:没有对变量求值,Lisp说没有变量“a”或“b”(可能是动态作用域的原因),因为它在宏展开的地方搜索变量。我想有一个解决方法。与defmacro
相比,什么是defmacro*
?Emacs给出了以下内容(使用“描述”函数):defmacro*是一个Lisp宏。(defmacro*名称ARGLIST[DOCSTRING]BODY…)将名称定义为宏。与普通的“defmacro”类似,除了ARGLIST允许完整的公共Lisp约定外,BODY被(块名…)或(let((cmd`(some…,a',b)))…)
@WillNess包围——是的,可能是这样。
(defun get-id ()
(send-command-to-process 'getid))
(do-something <a> <b> results)