Ruby有“的普遍想法感实性 ”和“ falsiness ”。
Ruby 确实有两个特定于Boolean对象的类,TrueClass
并且FalseClass
具有分别由特殊变量true
和表示的单例实例false
。
但是,真实性和虚假性不仅限于这两个类的实例,该概念是通用的,适用于Ruby中的每个对象。每个对象都是真实的或虚假的。规则很简单。特别是,只有两个对象是虚假的:
nil
,的一个实例,NilClass
以及false
,的单例实例FalseClass
每个其他对象都是真实的。这甚至包括在其他编程语言中被认为是虚假的对象,例如
这些规则是语言内置的,并且不是用户定义的。没有to_bool
隐式转换或类似的东西。
这是ISO Ruby语言规范的引文:
6.6布尔值
一个对象可以分为真对象或假对象。
只有false和nil是伪造的对象。false是该类的唯一实例
FalseClass
(请参见15.2.6),false表达式对其进行评估(请参见11.5.4.8.3)。nil是该类的唯一实例NilClass
(请参见15.2.4),一个nil-expression对其进行评估(请参见11.5.4.8.2)。除false和nil之外的其他对象均分类为真实对象。true是该类的唯一实例
TrueClass
(请参见15.2.5),true表达式将对其进行评估(请参见11.5.4.8.3)。
it "considers a non-nil and non-boolean object in expression result as true" do if mock('x') 123 else 456 end.should == 123 end
根据这两个来源,我认为Regexp
s也是真实的,但根据我的测试,它们不是:
if // then 'Regexps are truthy' else 'Regexps are falsy' end
#=> 'Regexps are falsy'
我在YARV 2.7.0-preview1,TruffleRuby 19.2.0.1和JRuby 9.2.8.0上进行了测试。这三种实现都彼此同意,不同意ISO Ruby语言规范和我对Ruby / Spec的解释。
更准确地说,Regexp
作为评估Regexp
文字的结果的对象是虚假的,而Regexp
作为其他表达式的结果的对象是真实的:
r = //
if r then 'Regexps are truthy' else 'Regexps are falsy' end
#=> 'Regexps are truthy'
这是错误还是期望的行为?
!!//
是错误的但是!!/r/
真实的。确实很奇怪。
!!/r/
生成false
。
//
in if // then
被解释为一个测试(的快捷方式if //=~nil then
)(无论采用哪种模式都总是虚假的),而不是一个Regexp实例。
Regex.new("a")
是事实。