不同 Lisps 之间的区别在于它们如何处理 true、false 和 nil。
在 Common Lisp 中,我们有t
true 和nil
false,尽管除此之外的所有内容nil
实际上都是真实的。如果列表是空的,或者find
什么都没有,我们有nil
,我们可以直接测试。技术术语是nil punning
。
'() ; => NIL
(= 1 2) ; => NIL
(if '() "full" "empty") ; => "empty"
(find 5 '(1 2 3 4)) ; => NIL
(if (find 5 '(1 2 3 4)) "found" "not found" ; => "not found"
Clojure 的做法不同。有一个正式的真值true
,有两个假值,false
并且- 除了和之外的nil
所有值也是真值。空列表不再是,您需要对空列表使用单独的测试,使用. 该值更像C 中的值。更好还是更差?- 你决定。false
nil
nil
empty?
nil
void
'() ; => ()
(= 1 1) ; => true
(= 1 2) ; => false
(if '() "full" "empty") ; => "full"
(if (empty? '()) "empty" "full") ; => "empty"
(if nil "full" "empty") ; => "empty"
(if (println "Hello world") "full" "empty") ; => empty
Scheme 在意图上更接近于 Clojure。这里有一个错误值,#f
。空列表不再是nil
,您需要对空列表使用单独的测试,使用null?
.
(= 1 1) ; => #t
(= 1 2) ; => #f
(null? '()) ; => #t
(null? 'nil) ; => #f
所以,null
是空列表的另一个名称,但nil
不是'nil
。
null ; => ()
nil ; => cannot reference an identifier before its definition
'nil ; => nil
怎么样(car ())
?您的方案nil
从评估返回()
,这car
就是抱怨的地方。我的计划,Racket 博士,根本拒绝演奏,说空列表中缺少表达式。