Consider this contrived example:
# Dispatch on value of fruit_kind:
TYPE_A = :apple
TYPE_B = :banana
TYPE_C = :cherry
eating_method = nil
case fruit_kind
# Methods to use for different kinds of fruit (assume these are
# already defined)
when TYPE_A then eating_method = bite
when TYPE_B then eating_method = peel
when TYPE_C then eating_method = om_nom_nom
end
Now I'd like to invoke the target of eating_method
with some arguments:
# Doesn't work; this tries to invoke a method called "eating_method",
# not the reference I defined earlier.
eating_method(some_fruit)
What's the right way to do this in Ruby?
Use send
. Send takes the function name, so use symbols:
case fruit_kind
# Methods to use for different kinds of fruit (assume these are
# already defined)
when TYPE_A then eating_method = :bite
when TYPE_B then eating_method = :peel
when TYPE_C then eating_method = :om_nom_nom
end
send(eating_method, some_fruit)
By the way, did you know you can make that case
a little prettier by doing something like this:
eating_method = case fruit_kind
# Methods to use for different kinds of fruit (assume these are
# already defined)
when TYPE_A then :bite
when TYPE_B then :peel
when TYPE_C then :om_nom_nom
else nil
end
Or, as Sii mentions, use a hash instead:
fruit_methods = {:apple => :bite, :banana => :peel, :cherry => :om_nom_nom}
send(fruit_methods[fruit_kind], some_fruit)