Isn't hash default value behavior just a little bizarre???

Discussion in 'Ruby' started by Farhad Farzaneh, Jul 4, 2007.

  1. Try this:

    >> x = Hash.new([])

    => {}
    >> x[:test]

    => []
    >> x[:test] << 'this'

    => ["this"]
    >> x[:bar]

    => ["this"]

    Huh? It seems that when I index a hash with a new key, it returns the
    Hash's default value object, not a copy of it. So if you modify that,
    it modifies the default value, which then effects the default value for
    every other new key.

    I don't know, I wouldn't call this the "principle of least surprise"...
    I was plenty surprised!

    --
    Posted via http://www.ruby-forum.com/.
     
    Farhad Farzaneh, Jul 4, 2007
    #1
    1. Advertising

  2. Re: Isn't hash default value behavior just a little bizarre?

    Peña, Botp wrote:

    >
    > ruby allows one to change the default value. that is good, imho.
    > i think the surprise stems fr the fact that it is _too simple to change
    > the default. hey, it's ruby ;)
    >
    > kind regards -botp


    You're right. Somehow I missed that in the documentation.... did RTFM,
    but obviously not carefully enough.

    Still, I do find it pretty surprising. I got stung when I was actually
    using the feature to initialize any entry to an array just to avoid the
    business of

    hash[key] ||= []

    Lesson learned.

    --
    Posted via http://www.ruby-forum.com/.
     
    Farhad Farzaneh, Jul 4, 2007
    #2
    1. Advertising

  3. Re: Isn't hash default value behavior just a little bizarre?

    T24gQmVoYWxmIE9mIEZhcmhhZCBGYXJ6YW5laDoNCiMgU3RpbGwsIEkgZG8gZmluZCBpdCBwcmV0
    dHkgc3VycHJpc2luZy4gIEkgZ290IHN0dW5nIHdoZW4gSSANCiMgd2FzIGFjdHVhbGx5IA0KIyB1
    c2luZyB0aGUgZmVhdHVyZSB0byBpbml0aWFsaXplIGFueSBlbnRyeSB0byBhbiBhcnJheSBqdXN0
    IHRvIA0KIyBhdm9pZCB0aGUgDQojIGJ1c2luZXNzIG9mDQojIA0KIyBoYXNoW2tleV0gfHw9IFtd
    DQoNCmp1c3QgYmUgY2FyZWZ1bCB3IGhhc2gjW108PCBtZXRob2QgKGJ1dCBub3QgdG9vIGNhcmVm
    dWwsIG90aGVyd2lzZSwgeW91IHdvdWxkIG5vdCBlbmpveSBydWJ5IDopLiBXaGF0IHlvdSByZWFs
    bHkgd2FudGVkIHRoZW4gd2FzIGhhc2gjW109DQoNCmlyYihtYWluKTowNDE6MD4geSA9IEhhc2gu
    bmV3DQo9PiB7fQ0KaXJiKG1haW4pOjA0MzowPiB5WzFdDQo9PiBuaWwNCmlyYihtYWluKTowNDQ6
    MD4geVsxXSA8PCAidGVzdCINCk5vTWV0aG9kRXJyb3I6IHVuZGVmaW5lZCBtZXRob2QgYDw8JyBm
    b3IgbmlsOk5pbENsYXNzDQogICAgICAgIGZyb20gKGlyYik6NDQNCiAgICAgICAgZnJvbSA6MA0K
    DQpoZXJlLCBzaW5jZSB5LmRlZmF1bHQgPT0gbmlsICBvciAgeVsxXSA9PSBuaWwsIHdlIGFyZSBh
    Y3R1YWxseSBkb2luZyAgbmlsIDw8ICJ0ZXN0IiB3YyBpcyBvYnZpb3VzbHkgd3JvbmcuDQoNCmly
    YihtYWluKTowNDU6MD4geVsxXSA9ICJ0ZXN0Ig0KPT4gInRlc3QiDQoNCnRha2UgYSBsb29rIGFs
    c28gYXQgaGFzaCNkZWZhdWx0DQo=
     
    Peña, Botp, Jul 4, 2007
    #3
  4. Farhad Farzaneh

    Alex Young Guest

    Re: Isn't hash default value behavior just a little bizarre?

    Farhad Farzaneh wrote:
    > Peña, Botp wrote:
    >
    >> ruby allows one to change the default value. that is good, imho.
    >> i think the surprise stems fr the fact that it is _too simple to change
    >> the default. hey, it's ruby ;)
    >>
    >> kind regards -botp

    >
    > You're right. Somehow I missed that in the documentation.... did RTFM,
    > but obviously not carefully enough.
    >
    > Still, I do find it pretty surprising. I got stung when I was actually
    > using the feature to initialize any entry to an array just to avoid the
    > business of
    >
    > hash[key] ||= []
    >

    Apologies if you've already come across this, but I think the correct
    way to do what you're trying to do is this:

    h = Hash.new(){|h,k| h[k] = []}

    The block passed to Hash.new gets called for each new entry in the hash,
    so a new array will be constructed each time.

    Hope this helps,
    --
    Alex
     
    Alex Young, Jul 4, 2007
    #4
  5. Re: Isn't hash default value behavior just a little bizarre?

    Alex Young wrote:
    > Apologies if you've already come across this, but I think the correct
    > way to do what you're trying to do is this:
    >
    > h = Hash.new(){|h,k| h[k] = []}
    >
    > The block passed to Hash.new gets called for each new entry in the hash,
    > so a new array will be constructed each time.
    >
    > Hope this helps,


    Sweet. Now that looks very Ruby'ish! Thanks.

    --
    Posted via http://www.ruby-forum.com/.
     
    Farhad Farzaneh, Jul 4, 2007
    #5
  6. Farhad Farzaneh

    Guest

    Re: Isn't hash default value behavior just a little bizarre?

    ---2049402039-369337158-1183547419=:6742
    Content-Type: MULTIPART/MIXED; BOUNDARY="-2049402039-369337158-1183547419=:6742"

    This message is in MIME format. The first part should be readable text,
    while the remaining parts are likely unreadable without MIME-aware tools.

    ---2049402039-369337158-1183547419=:6742
    Content-Type: TEXT/PLAIN; charset=X-UNKNOWN; format=flowed
    Content-Transfer-Encoding: QUOTED-PRINTABLE

    Hi --

    On Wed, 4 Jul 2007, Farhad Farzaneh wrote:

    > Pe=C3=B1a, Botp wrote:
    >
    >>
    >> ruby allows one to change the default value. that is good, imho.
    >> i think the surprise stems fr the fact that it is _too simple to change
    >> the default. hey, it's ruby ;)
    >>
    >> kind regards -botp

    >
    > You're right. Somehow I missed that in the documentation.... did RTFM,
    > but obviously not carefully enough.
    >
    > Still, I do find it pretty surprising.


    All you're doing is assigning an object to a certain role. There's no
    implication of automatic duplication of the object.

    > I got stung when I was actually
    > using the feature to initialize any entry to an array just to avoid the
    > business of
    >
    > hash[key] ||=3D []


    It doesn't do that anyway:

    h =3D {}
    h.default =3D []
    p h["blah"] # [] (default value for undefined key)
    p h # {} (no keys are defined)

    The default value is for undefined keys, whereas hash[key] ||=3D []
    actually sets a key.


    David

    --=20
    * Books:
    RAILS ROUTING (new! http://www.awprofessional.com/title/0321509242)
    RUBY FOR RAILS (http://www.manning.com/black)
    * Ruby/Rails training
    & consulting: Ruby Power and Light, LLC (http://www.rubypal.com)
    ---2049402039-369337158-1183547419=:6742--
    ---2049402039-369337158-1183547419=:6742--
     
    , Jul 4, 2007
    #6
  7. Re: Isn't hash default value behavior just a little bizarre?

    unknown wrote:
    > Hi --
    >
    >
    > All you're doing is assigning an object to a certain role. There's no
    > implication of automatic duplication of the object.


    I was thinking of it as initialization of the value of the item
    accessed, but when you think of it as *the* default object it makes
    sense.

    >
    >> I got stung when I was actually
    >> using the feature to initialize any entry to an array just to avoid the
    >> business of
    >>
    >> hash[key] ||= []

    >
    > It doesn't do that anyway:
    >
    > h = {}
    > h.default = []
    > p h["blah"] # [] (default value for undefined key)
    > p h # {} (no keys are defined)
    >
    > The default value is for undefined keys, whereas hash[key] ||= []
    > actually sets a key.
    >


    The misunderstanding on my part was that I thought it initialized the
    key to the default object, rather than returned the actual default
    object. In this context, if the key is automatically initialized to an
    empty array, then when I wanted to assign something to it, I wouldn't
    have to first make it an array.


    --
    Posted via http://www.ruby-forum.com/.
     
    Farhad Farzaneh, Jul 4, 2007
    #7
  8. Re: Isn't hash default value behavior just a little bizarre?

    "Farhad Farzaneh" <> wrote in message
    news:...
    > Peña, Botp wrote:
    >
    >>
    >> ruby allows one to change the default value. that is good, imho.
    >> i think the surprise stems fr the fact that it is _too simple to change
    >> the default. hey, it's ruby ;)
    >>
    >> kind regards -botp

    >
    > You're right. Somehow I missed that in the documentation.... did RTFM,
    > but obviously not carefully enough.
    >
    > Still, I do find it pretty surprising. I got stung when I was actually
    > using the feature to initialize any entry to an array just to avoid the
    > business of
    >
    > hash[key] ||= []
    >
    > Lesson learned.


    I don't recall Ruby ever sacrificing power for Principle of Least
    Surprise (indeed, it's arguable that this isn't even one of Ruby's design
    goals...).
    In particular, there are times (although not common) where you do want
    the default value to be shared across key entries, in which case, Ruby
    currently allows you to do so. Suppose Ruby behaved as you expected. How
    would you do this? I think you'll quickly see that you can't and you will,
    thus, see why Ruby does what it does...
     
    Just Another Victim of the Ambient Morality, Jul 5, 2007
    #8
  9. Re: Isn't hash default value behavior just a little bizarre?

    Logan Capaldo wrote:
    > On 7/4/07, Farhad Farzaneh <> wrote:
    >> => ["this"]
    >> Posted via http://www.ruby-forum.com/.
    >>
    >>

    > Copying is an interesting thing. For many objects there is a sane,
    > obvious
    > way to make a copy. But for many others it is not so clear. Consider for
    > instance, Hash.new($stdin). What should it mean, in this context, to
    > "copy"
    > $stdin? Or consider Hash.new(some_very_large_object). Do you want a copy
    > all
    > the time? Luckily, Hash does have a mechanism to acheive what you want:
    >
    >>> x = Hash.new { |h,k| h[k] = [] }

    > => {}
    >>> x[:test]

    > => []
    >>> x[:test] << 'this'

    > => ["this"]
    >>> x[:bar]

    > => []
    >
    > POLS also is matz.'s POLS.


    Current behavior does (of course) make sense, and my confusion was due
    to my misunderstanding of the feature and its intended use.

    Thanks to all.



    --
    Posted via http://www.ruby-forum.com/.
     
    Farhad Farzaneh, Jul 5, 2007
    #9
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Replies:
    5
    Views:
    754
  2. =?Utf-8?B?QmFobWFu?=

    Bizarre behavior

    =?Utf-8?B?QmFobWFu?=, Mar 3, 2006, in forum: ASP .Net
    Replies:
    2
    Views:
    422
    =?Utf-8?B?QmFobWFu?=
    Mar 6, 2006
  3. Jay
    Replies:
    12
    Views:
    671
  4. bukzor
    Replies:
    37
    Views:
    906
  5. rp
    Replies:
    1
    Views:
    562
    red floyd
    Nov 10, 2011
Loading...

Share This Page