如何在Common Lisp中将s-exp传递给非s-exp类型的参数?

时间:2014-08-25 05:00:31

标签: common-lisp

问题:如何在传递给期望字符串类型参数的函数之前强制评估s-exp。

此代码没问题(没有错误):

(setf (slot-value (ole sheet :range "A1:B1") 'value)
   `(("123" "456"))))  

然而,当传递诸如(第一行)而不是“123”的s-exp时:

(setf line '("123" "456"))

(setf (slot-value (ole sheet :range "A1:B1") 'value)
   `(((first line) (second line))))) 

有错误消息:

  

值FIRST不是预期类型(OR                                               串                                               Fixnum对象                                               单精度浮点数                                               双浮子)。     [TYPE-ERROR类型的条件]

     

重新启动:   0:[重试]重试SLIME REPL评估请求。   1:[* ABORT]返回SLIME的顶级。   2:[ABORT-BREAK]重置此线程   3:[ABORT]杀掉这个帖子

我知道问题是什么。但有没有办法摆脱这种限制?因为我们需要将代码行放在循环中,所以无法修改参数值,例如“123”...

我尝试使用宏:

(defmacro set-line (par1 par2)
  `(setf (slot-value (ole sheet :range "A1:B1") 'value)
     `((,par1 ,par2))))

然而,它不起作用。仍然是相同的错误消息说错了类型(第一行)......

(set-line (first line) (second line))

如果它出现在宏体内,我也不知道如何逃避反引号。我已经尝试在宏体内部的反引号前面放一个\,然后在宏展开时也会出现\。

`(setf xxx  `  <--- another backquote 
`(setf xxx  \`  <--- this can't escape backquote inside macro body

感谢。

背景:在使用Win32 OLE Excel示例时: https://github.com/quek/cl-win32ole/blob/master/example/excel.lisp

1 个答案:

答案 0 :(得分:3)

您缺少引用的基础知识。你的表达

? `(("123" "456")) ; quasiquote
(("123" "456"))

是包含列表的列表,也可以使用函数LIST作为

创建
? (list (list "123" "456")) ; list
(("123" "456"))

要使用表达式,您可以使用unquote(请注意前面的逗号)

? `((,(first line) ,(second line))) ; quasiquote with unquote
(("123" "456"))

或更好

? `(,line)
(("123" "456"))

或使用list

? (list line)
(("123" "456"))