common-lisp - 如何更改 aif 以能够在宏调用中访问 'it' 而无需在包中公开 'it'

标签 common-lisp

如果您将 onlisp 中提供的 aif 代码放入在一个包中并尝试在另一个包中使用它,您遇到的问题是 packagename:it is not external.

(in-package :packagename)

(defmacro aif (test-form then-form &optional else-form)
  ‘(let ((it ,test-form))
     (if it ,then-form ,else-form)))

需要的调用语法

(in-package :otherpackage)

(aif (do-stuff)
  (FORMAT t "~a~%" it)
  (FORMAT t "just got nil~%"))

我怎样才能在代码中修复这个行为,而不是在包声明中将变量设置为外部变量,并且能够通过 it 而不是 访问 it包名:它?

最佳答案

(defmacro aif (test then &optional else)
  ;;; read-from-string will intern the symbol
  ;;; in the current package, with the correct
  ;;; read-table-case
  (let ((it (read-from-string "it")))
    `(let ((,it ,test))
       (if ,it ,then ,else))))

或者这也行:

(defmacro aif (test then &optional else)
  ;;; (intern "IT") or (intern "it") will work
  ;;; as well, depending on your readtable settings.
  ;;; using string or symbol-name gets around that.
  (let ((it (intern (string 'it))))
    `(let ((,it ,test))
       (if ,it ,then ,else))))

关于common-lisp - 如何更改 aif 以能够在宏调用中访问 'it' 而无需在包中公开 'it',我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12391776/

相关文章:

lisp - Lisp 文件扩展名的约定是什么?

error-handling - 在 SBCL 中使用 [Take New] 重新启动

common-lisp - uiop :launch-program and nodejs

sorting - 冒泡排序 Common Lisp 错误

scheme - 意外的数据持久性

list - 如何用 nil 创建点对

list - 如何在 Common Lisp 中迭代两个长度不等的列表

common-lisp - NP-完全开胃菜错误

algorithm - SBCL Lisp 在运行时将类型归因于内部循环。我该如何覆盖它?

lisp - 如何在 common lisp 中递归附加列表?