Question

I'd like to allow the user to pass an option to a method that can be either a single object or an array. The below code works, assuming `opts[:variable_length_opt] is defined:

def initialize(opts={})
  @ivar = *opts[:variable_length_opt]
end

But I'd also like to be able to set a default if the option is not set. But this code does not work:

def initialize(opts={})
  @ivar = (opts[:variable_length_opt] ? *opts[:variable_length_opt] : default_value)
end

It throws an unexpected tSTAR error. I understand there are other, more verbose methods to accomplish what I'm after, but I am wondering if there are other, as-short alternatives. Also, what are the limits of the splat? I can't think of a good reason that it should be unavailable here.

Was it helpful?

Solution

I think splats are only available in assignments (and indirectly, in method calls). You can't call splat directly either:

1.9.3p286 :045 > *[1,2,3,4]
SyntaxError: (irb):45: syntax error, unexpected '\n', expecting tCOLON2 or '[' or '.'
    from /Users/fcoury/.rvm/rubies/ruby-1.9.3-p286/bin/irb:16:in `<main>'

In your case, you can do something like:

def initialize(opts={})
  @ivar = *(opts[:variable_length_opt] ? opts[:variable_length_opt] : [default_value])
end

That is almost as short.

But you usually use the splat to assign multiple variables from an array, like

a = [1,2,3,4]
b, c, d, e = *a
b #=> 1
c #=> 2 ...

Why do you need the splat in this case?

OTHER TIPS

Instead of using ternary actually you could initialize your opts hash with a default value -

class InitOptions
    attr_reader :ivar

    def initialize(opts=Hash.new("default_value"))
        @ivar = *opts[:variable_length_opt]
    end
end

p InitOptions.new({:variable_length_opt => [1,2,3,4]}).ivar #=> [1, 2, 3, 4]
p InitOptions.new.ivar # => ["default_value"]

What Hash.new("default_value") does is that instead of returning nil when some key in not present in the hash, it returns whatever value you passed to initialize it, in this case default_value

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top