views:

331

answers:

3

Can't seem to find how to check if an object is a boolean easily. Is there something like this in Ruby?

true.is_a?(Boolean)
false.is_a?(Boolean)

Right now I'm doing this and would like to shorten it:

some_var = rand(1) == 1 ? true : false
(some_var.is_a?(TrueClass) || some_var.is_a?(FalseClass))
+2  A: 

There is no Boolean class in Ruby, the only way to check is to do what you're doing (comparing the object against true and false or the class of the object against TrueClass and FalseClass). Can't think of why you would need this functionality though, can you explain? :)

If you really need this functionality however, you can hack it in:

module Boolean; end
class TrueClass; include Boolean; end
class FalseClass; include Boolean; end

true.is_a?(Boolean) #=> true
false.is_a?(Boolean) #=> true
banister
trying to do typecasting based on the current value.
viatropos
+1  A: 

As stated above there is no boolean class just TrueClass and FalseClass however you can use any object as the subject of if/unless and everything is true except instances of FalseClass and nil

Boolean tests return an instance of the FalseClass or TrueClass

(1 > 0).class #TrueClass

The following monkeypatch to Object will tell you whether something is an instance of TrueClass or FalseClass

class Object
  def boolean?
    self.is_a?(TrueClass) || self.is_a?(FalseClass) 
  end
end

Running some tests with irb gives the following results

?> "String".boolean?
=> false
>> 1.boolean?
=> false
>> Time.now.boolean?
=> false
>> nil.boolean?
=> false
>> true.boolean?
=> true
>> false.boolean?
=> true
>> (1 ==1).boolean?
=> true
>> (1 ==2).boolean?
=> true
Steve Weet
Simpler just to write `self == true or self == false`. Those are the only instances of TrueClass and FalseClass.
Chuck
@chuck that returns the same results except for Time.now.boolean? which returns nil. Any idea why?
Steve Weet
Defining a class check on self in the method is somewhat not oop. You should define two versions of `boolean`, one for TrueClass/FalseClass and one for Object.
Konstantin Haase
The reason is that a bug in the version of `Time#==` in Ruby 1.8 causes a comparison to non-Time values to return nil rather than false.
Chuck
+2  A: 

Simplest way I can think of:

# checking whether foo is a boolean
!!foo == foo
Konstantin Haase