Common Lisp:#+nil 是什么意思?

Common Lisp: What does #+nil?

前几天(也许是昨天)我对在 https://github.com/billstclair/defperson/blob/master/defperson.lisp#L289.

中发现的这个 #+nil 读时条件感到很困惑

经过深思熟虑,我得出的结论是,这是注释掉 代码的非常不灵活的方式。有人可以证实这一点吗?

也许我的假设是完全错误的。无论如何,先谢谢了。

CLHS 2.4.8.17 Sharpsign Plus

为了条件化从输入中读取表达式,Common Lisp 使用了特性 expressions

在这个例子中,它被用来注释掉一个表单。

它是 reader 的一部分。 #+ 查看下一项(通常作为具有相同名称的关键字符号)是否是列表 *features* 的成员。如果是,则正常读取下一项,如果不是,则跳过。通常 :NIL 不是该列表的成员,因此跳过该项目。因此它对 Lisp 隐藏了表达式。可能有一个 Lisp 实现,但它不起作用:NILLisp 的新实现。它可能在 *features* 列表中有符号 :NIL,以指示实现的名称。

NIL 等功能默认在 keyword 包中读取:

  • #+NIL -> 在 cl:*features*
  • 中寻找 :NIL
  • #+CL:NIL -> 在 cl:*features*
  • 中寻找 CL:NIL

例子

(let ((string1 "#+nil foo bar"))             ; string to read from

  (print (read-from-string string1))         ; read from the string

  (let ((*features* (cons :nil *features*))) ; add :NIL to *features*
    (print (read-from-string string1)))      ; read from the string

  (values))                                  ; return no values

它打印:

BAR 
FOO 

请注意,Common Lisp 还有其他注释形式的方法:

; (sin 3) should we use that?

#| (sin 3)  should we use that?
   (cos 3)  or this?            |#

Yes, it is a lispy way of commenting code,但您不应该在生产代码中遗漏它。

更好的选择是 #+(or)

它只需要多一个字符,如果你使用 Emacs paredit 或其他一些自动插入右括号的模式,它需要相同的按键,并且它不受符号 :nil 中存在的限制*features*.