У Рубі є універсальне уявлення про « правдивість » та « хибність ».
Рубін робить два конкретних класів для об'єктів Boolean, TrueClassі FalseClass, з одноплідними випадками , позначених спеціальними змінними trueі false, відповідно.
Однак правдивість і хибність не обмежуються примірниками цих двох класів, концепція є універсальною і застосовується до кожного об'єкта в Ruby. Кожен об'єкт є або truthy або falsy . Правила дуже прості. Зокрема, лише два об'єкти є хибними :
nil, одиничний екземплярNilClassіfalse, одиночний екземплярFalseClass
Кожен інший об'єкт є правдою . Сюди входять навіть об'єкти, які вважаються хибними в інших мовах програмування, наприклад
Ці правила вбудовані в мову і не визначаються користувачем. Немає to_boolнеявного перетворення чи нічого подібного.
Ось цитата зі специфікації мови ISO Ruby :
6.6 Булеві значення
Об'єкт класифікується або в істинний об'єкт, або в хибний об'єкт .
Тільки брехня і нуль є falseish об'єктів. false - єдиний екземпляр класу
FalseClass(див. 15.2.6), для якого оцінюється хибний вираз (див. 11.5.4.8.3). nil - єдиний екземпляр класуNilClass(див. 15.2.4), якому оцінюється вираження nil (див. 11.5.4.8.2).Об'єкти, крім БРЕХНІ і нуля підрозділяється на trueish об'єкти. true - єдиний екземпляр класу
TrueClass(див. 15.2.5), якому оцінюється істинний вираз (див. 11.5.4.8.3).
Виконаний файл Ruby / Spec, схоже, згоден :
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
Згідно з цими двома джерелами, я б припустив, що Regexps також є непростими , але згідно з моїми тестами, вони не:
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 Language та моїм тлумаченням Ruby / Spec.
Точніше, Regexpоб'єкти, які є результатом оцінювання Regexp літералів, є хибними , тоді як Regexpоб'єкти, які є результатом якогось іншого виразу, є правдою :
r = //
if r then 'Regexps are truthy' else 'Regexps are falsy' end
#=> 'Regexps are truthy'
Це помилка чи бажана поведінка?
!!//помилково, але !!/r/є правдою. Дивно насправді.
!!/r/виробляє falseдля мене, використовуючи (RVM) Ruby 2.4.1.
//в if // thenінтерпретується як тест (ярлик для if //=~nil then) (який завжди хибний, незалежно від шаблону), а не як екземпляр Regexp.
Regex.new("a")це правда.