【问题标题】:If nil is treated as a logical false in Clojure, why does (false? nil) return false如果在 Clojure 中将 nil 视为逻辑 false,为什么 (false? nil) 返回 false
【发布时间】:2021-04-30 11:23:00
【问题描述】:

Living Clojure一书解释说,nil 类型被视为逻辑假。

所以我预计 (false? nil) 会返回 true,但事实并非如此。 (true? nil) 也没有。两者都返回false,这让我认为Clojure 将nil 视为既不是true 也不是false

另一方面,(not nil) 的计算结果为 true。所以我有点困惑。

【问题讨论】:

    标签: clojure


    【解决方案1】:

    区别在于测试逻辑真理,而不是本身。

    nilfalse 在 Clojure 中被视为逻辑错误。所有其他值都被视为逻辑上正确

    谓词false?true? 分别显式测试 falsetrue,正如您所指出的。这些谓词在 Clojure 中不常用。

    【讨论】:

      【解决方案2】:

      根据documentation of false?

      如果 x 的值为 false,则返回 true,否则返回 false。

      所以该函数检查参数是否等于值false,而不是检查它是否为logically false

      在 Clojure 中,所有值要么在逻辑上为真,要么在逻辑上为假,因此它们可以在条件表达式中使用。唯一逻辑错误的值是nilfalse

      【讨论】:

        【解决方案3】:

        已经有一些很好的答案了。

        人们有时使用术语 falseynilfalse)和 truthy(所有其他值)来描述 Clojure 值。 有时将值强制转换为布尔值 truefalse 很方便。我什至为此写了a handy function

        (defn truthy?
          "Returns true if arg is logical true (neither nil nor false); otherwise returns false."
          [arg]
          (if arg true false))
        
        (defn falsey?
          "Returns true if arg is logical false (either nil or false); otherwise returns false. Equivalent
           to (not (truthy? arg))."
          [arg]
          (if arg false true))
        

        这些有时在过滤值或构造 true/false 值的向量时很方便。 后来,我发现 Clojure 已经有了一个函数 boolean,它和 truthy? 做同样的事情。

        请务必查看this list of documentation sources,尤其是 Clojure CheatSheet。尽情享受吧!

        【讨论】:

        • 除非对于某些 DSL,我只使用 booleannot 而不是发明更冗长的东西。
        【解决方案4】:

        Living Clojure 一书解释了nil 类型被处理 与逻辑false 相同。

        首先,nil 是一个值,而不是一个类型。

        • 它的类型是无名的。
        • 任何引用(对象)类型都可以将其作为值。

        其次,nilfalse 是不同的值。您可以轻松编写以不同方式处理它们的代码:

        (map #(case %, nil 1, false 2) [nil false])
        => (1 2)
        

        nil,例如,双关语是一个空序列,

        (count nil)
        => 0
        

        false 没有

        (count false)
        Execution error ...
        

        作为if 的第一个参数,nil 等价于false

        转述the official document

        (if test then else?)
        

        ...计算test,然后...

        • 如果是nilfalse,则计算并生成else
        • 否则计算并生成then

        如果未提供else,则默认为nil

        所有其他条件句(whenif-letcond、 ...) 遵循相同的逻辑:

        • nilfalse构成逻辑错误;
        • 其他一切都构成逻辑真理。

        至于谓词函数false?,可能已经定义了……

        (defn false? [x]
          (case x, false true, false))
        

        ... 对于除精确值 false 之外的任何参数,返回 false

        顺便说一句,Clojure 值 falsetrue 是 Java 对象 Boolean/FALSEBoolean/TRUE

        Boolean/FALSE
        => false
        (if Boolean/FALSE 1 2)
        => 2
        (type false)
        => java.lang.Boolean
        

        【讨论】:

          猜你喜欢
          • 2011-06-26
          • 1970-01-01
          • 2016-02-13
          • 1970-01-01
          • 2023-04-04
          • 1970-01-01
          • 2013-09-18
          • 2015-11-11
          • 2013-01-07
          相关资源
          最近更新 更多