From: Stefano Crocco Date: 2010-07-06T20:36:11+09:00 Subject: Re: WTF? Case statement disfunctional? On Tuesday 06 July 2010, Pieter Hugo wrote: > |Hi > | > |I have a simple problem with the class of an object not being recognised > |by the case statement. Am I just being an idiot again or is there > |something more sinister going on here? > | > |a=1 > |case a.class > | when Fixnum > | puts "It's a number silly" > | else > | puts "Can't figure it out" > |end > | > |This snippet of code returns "Can't figure it out" which is just wrong? > | > |a.is_a? Fixnum => true and a.class => fixnum and a.class == Fixnum => > |true, so why dont my case statement work? > | > |case a.class.to_s > | when "Fixnum" > |... > | > |does the trick, but it just offends my aesthetics. > | > |Any ideas? Comments? > | > |Regards > | > |Pieter Hugo > |South Africa In a case expression, to decide which of the branches should be executed, ruby calls the === method of the object after each when clause, passing as argument the object after the case clause: the branch which will be executed is the first one for which this method returns true. What does this mean in your code? It means that ruby will call Fixnum.=== passing it a.class, which means Fixnum. But Fixnum.===, which is the same as Class#=== since Fixnum is an instance of Class, returns true if the argument is an instance of Fixnum and false otherwise. Of course, Fixnum is not an instance of Fixnum, so that branch is not executed. To achieve what you want, you need to write case a rather than case a.class This way, the object passed to Fixnum.=== will be a, which is indeed an instance of Fixnum. It is very easy to be confounded by this issue (it also happens to me from time to time). I hope this helps Stefano