Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How does the 'case' statement work with constants?

I am using Ruby 1.9.2 and Ruby on Rails 3.2.2. I have the following method:

# Note: The 'class_name' parameter is a constant; that is, it is a model class name.
def my_method(class_name)
  case class_name
  when Article then make_a_thing
  when Comment then make_another_thing
  when ...     then ...     
  else raise("Wrong #{class_name}!")
  end  
end

I would like to understand why, in the case statement above, it always runs the else "part" when I execute method calls like my_method(Article), my_method(Comment) and so on.

How can I solve the issue? Does someone have advice how to handle this?

like image 610
user12882 Avatar asked Oct 23 '12 00:10

user12882


1 Answers

This is because case calls ===, and === on Class (or specifically Module, which Class descends from) is implemented like so:

mod === objtrue or false

Case Equality—Returns true if obj is an instance of mod or one of mod’s descendants. Of limited use for modules, but can be used in case statements to classify objects by class.

This means that for any constant except Class & Module (e.g. Foo), Foo === Foo always returns false. As a result, you always get the else condition in your case statement.

Instead just call case with the object itself, instead of its class, or use if statements.

like image 135
Andrew Marshall Avatar answered Oct 18 '22 16:10

Andrew Marshall