【问题标题】:Ruby boolean double negation conventionRuby 布尔双重否定约定
【发布时间】:2011-04-26 21:47:08
【问题描述】:

谁能告诉我为什么很多 Ruby 布尔方法都使用这种双重否定约定?

!!(boolean expression)

【问题讨论】:

标签: ruby


【解决方案1】:

双重否定确保无论初始值如何,您总是会得到truefalse,绝不是什么神秘值。

这很方便,因为它避免了对不再需要的对象的悬空引用,或者不必区分两种类型的错误值,nilfalse

你经常会看到这样写的方法:

def logged_in?
  !!@session_user
end

这将返回truefalse,并且该值可用于任何需要的目的。与此比较:

def logged_in?
  @session_user
end

在这种情况下,如果您保存该值,您实际上是在保存整个 @session_user 对象,这可能是相当大的内存块。在您对它的引用超出范围之前,无法释放此内存。由于只有一个true 和一个false,所以不需要垃圾回收。

【讨论】:

    【解决方案2】:

    假设您要定义一个返回布尔值的方法。例如,字符串是否匹配正则表达式。

    class String
      def include? regex; self =~ regex end
    end
    

    如上,不匹配时返回nil,匹配时返回整数。在许多情况下,这并不重要(nil 类似于false 并且true 可以替换为整数)。但是如果你真的想要一个布尔值作为返回值,如果你这样做了

    class String
      def include? regex; !!(self =~ regex) end
    end
    

    匹配时返回true,不匹配时返回false

    【讨论】:

      【解决方案3】:

      在我看来,Ruby 在布尔运算方面有点太聪明了。这是聪明导致问题的解决方法。

      这就是过度的聪明之处:没有布尔类。相反,有一个约定 any 值可以用作布尔值。在需要真或假值的上下文中,nilfalse 表示“假”,其他任何内容都表示“真”。 truefalse 值不是特殊类的一部分,它们是各自类的唯一成员——它们的存在只是为了使代码更具可读性。

      我想这在大多数情况下都可以正常工作,但每隔很长一段时间你就需要一个 总是 truefalse 的布尔值。例如,我最近需要比较两个布尔值并在它们不同时做一些特别的事情;唯一的问题是,其中一个是truefalse,而另一个是1 或nil。使固定?利用!!nil == false!!1 == true 的事实。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-06-24
        • 2010-11-18
        • 2018-01-04
        • 2018-07-18
        • 2016-08-31
        • 2018-08-31
        • 2018-03-01
        相关资源
        最近更新 更多