lisp - 反引号扩展列表中的一系列元素

标签 lisp common-lisp clisp

假设我有一个结构(它的参数比这里显示的多):

(defstruct location
  name)

以及使用反引号定义一系列位置的关联列表:

(defparameter *locations* `(
  (ASIA ,(make-location :name "Asia"))
  (AFRICA ,(make-location :name "Africa"))
  )

这工作正常并正确地创建了位置结构。问题是,我计划有很多位置,而不是手动输入所有位置:

(defparameter *locations* `(
  (ASIA ,(make-location :name "Asia"))
  (AFRICA ,(make-location :name "Africa"))
  (LOC1 ,(make-location :name "Location 1"))
  ; Lots more...
  (LOC1024 ,(make-location :name "Location 1027"))
  )

很多这些额外的位置都有相似的参数,这样我就可以定义一个“生成器函数”来创建它们的列表:

(defun generate-locations (symbol name count)
  (loop for i from 1 to count collect (list
    (read-from-string (format nil "~A~D" symbol i))
    (make-location :name name))))

;;; Creates list ((LOC1 #S(LOCATION :NAME "Location 1")) (LOC2 ...
(generate-locations "LOC" "Location " 1024)

然后我尝试做类似的事情:

(defparameter *locations* `(
  (ASIA ,(make-location :name "Asia"))
  (AFRICA ,(make-location :name "Africa"))
  ,(generate-locations "LOC" "Location " 1024)
  )

不起作用,因为 GENERATE-LOCATIONS 返回一个列表,而不是随后可以添加的系列元素 到一个列表。所以我尝试VALUES-LIST它:

(defparameter *locations* `(
  (ASIA ,(make-location :name "Asia"))
  (AFRICA ,(make-location :name "Africa"))
  ,(values-list (generate-locations "LOC" "Location " 1024))
  )

这只会将第一个生成的位置添加到 *LOCATIONS*。我假设这是因为除了第一个 VALUES-LIST 之外的所有返回值都被忽略了。

那么如何正确地将一系列元素添加到*LOCATIONS*呢? GENERATE-LOCATIONS 应该是一个宏吗?如果是这样,它将如何构建?

最佳答案

需要使用拼接反引号操作符,@。在你的例子中:

(defparameter *locations* `(
  (ASIA ,(make-location :name "Asia"))
  (AFRICA ,(make-location :name "Africa"))
  ,@(generate-locations "LOC" "Location " 1024)
  )

为此,generate-locations 应该返回一个列表。 ,@ 会将每个项目拼接到周围的列表中,而不是将其作为单个项目插入。

关于lisp - 反引号扩展列表中的一系列元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18950957/

相关文章:

lisp - 生成二元约束满足问题的随机实例

recursion - 如何评估递归宏定义

common-lisp - 如果正在使用该函数,SBCL 何时会用更新的版本替换已编译的函数?

lisp - 需要了解带递归的 LISP 程序

functional-programming - 排列闭包树的输出

macros - 编写宏时获取原始符号名称

postgresql - CLSQL 中带有 select 函数的子查询

lisp - Common Lisp : How to check set equality, 忽略顺序?

使用 +、-、* 和/对表达式执行符号和数字运算的 LISP 函数

lisp - 包的文件在哪里?