Bug #11771
closed
unable to pass keyargs to []=
Added by bughit (bug hit) over 8 years ago.
Updated over 8 years ago.
Description
module Foo
def self.[]=(key, val, option: nil)
end
end
Foo[:key] = 1 # ok
Foo[:key, option: 1] = 1 # wrong number of arguments (3 for 2)
if you declare the []= params using *
module Bar
def self.[]=(*args)
p args
end
end
Bar[:key, option: 1] = 1 # args: [:key, {:option=>1}, 1]
the args end up [:key, {:option=>1}, 1] which seems wrong since the keyargs hash is supposed to be last
Affects back to 2.0 (when keyword args were introduced),
so this doesn't seem to be an optimization bug introduced in 2.1/2.2
I'm actually not sure about the specs and if there's some special case
for kwargs interacting with aref/aset...
For instance, frequently use the 'sequel' API to write stuff like:
DB[:tbl][id: 123]
(I've been doing this since before keyword args were introduced)
Eric Wong wrote:
Affects back to 2.0 (when keyword args were introduced),
so this doesn't seem to be an optimization bug introduced in 2.1/2.2
I'm actually not sure about the specs and if there's some special case
for kwargs interacting with aref/aset...
The problem here is that the []= syntax compiled into a method dispatch where positional value arg is passed last, after keyargs, something you can't even do in ruby.
you can simulate the bug with a plain method:
def foo(key, val, option: nil)
end
foo(:key, 1, option: 1) # ok
foo(:key, {option: 1}, 1) # wrong number of arguments (3 for 2)
- Status changed from Open to Closed
Pending, for several reasons:
(1) compatibility. a[a,foo:1]=v
is valid code. changing behavior may crash existing code.
(2) you can delegate to other method e.g.
def opt_aset(k,v,option:nil)
...
end
def []=(k,opt={},v)
opt_aset(k,v,*opt)
end
Matz.
Yukihiro Matsumoto wrote:
Pending, for several reasons:
(1) compatibility. a[a,foo:1]=v
is valid code. changing behavior may crash existing code.
(2) you can delegate to other method e.g.
def opt_aset(k,v,option:nil)
...
end
def []=(k,opt={},v)
opt_aset(k,v,*opt)
end
Matz.
def []=(k,opt={},v)
feels wrong because you're taking a dependency on incorrect behavior (method dispatch that puts a positional arg after the keyargs) Why not correct it for 3.0?
I don't say anything about 3.0 for now.
But things are more complicated than you imagine.
Matz.
Also available in: Atom
PDF
Like0
Like0Like0Like0Like0Like0