While doing some work with define_method today, I was looking for a way to specify blocks with default argument values so that I could define methods with default argument values.  It seems that Ruby doesn’t support this doing this:

 1 2 3 4 
# Does NOT work
define_method :method_name do |first_arg=“default1”, second_arg=“default2”|
  # …
end
This is mainly because of some limitations with yacc, which Ruby uses (says matz):
 1 2 3 4 5 6 
Mostly because yacc does not allow it. It confuses
 lambda { |foo = bar| puts foo }
as
 lambda { |foo = (bar| puts foo) }
and causes syntax error.
 
Anyways, I’ve found that these two approaches work:

 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 
# Using optional arguments, with a default value for “two”
define_method :method_name do |required, *optional|
  # one, two, = *optional
  one, two, *ignored = *optional
  # two will have a default value
  two ||= “Default value”
  
  # …
end
 
# With an options hash, with default values for the options
define_method :method_name do |required, *options|
  default_options = { :foobar => “default value }
options = (options.first || Hash.new).merge(default_options)
foobar = options[:foobar]
end
 
I wonder if anybody has a better way to do this

Posted via email from Tim says what? | Comment »