Guillaume Cottenceau wrote:
> Hi,
> 
> 
> I have a loop in which I'd like to populate a Hash by pushing back new
> elements to Arrays.
> 
> The problem is when I try to push back an element, because the default
> element "references" the default, which is an empty array, the action is
> only to make the default enlarges, not what I want :-).
> 
> 
> irb> h = Hash.new([])
> {}
> irb> h["banana"].push(1)

h["banana"] returns the default value [] but do not set the Hash key, 
thus your code does nothing else than:

  a = []
  a.push(1)

What you want would be

h["banana"] <<= 1     # => [1]

which equals to

h["banana"] = h["banana"].push(1)

But that do not work correctly with Ruby 1.6, because the
same object [] is returned for each default value.

In Ruby 1.7 there is (as far as I know) the possibility to
specify the default value as code-block such as

h = Hash.new { [] } 

In this case my code above would work as expected.


But what you can do is the following (which works with Ruby 1.6):

h = Hash.new
(h["banana"] ||= []).push(1)
(h["apple"] ||= []).push(1)


> As far as I looked, the default value must be an object, it can't be set
> to something callable (proc) each time we need the default.

Thats the real problem. Each time the same object is returned as default value.


Regards,

  Michael

-- 
Michael Neumann
merlin.zwo InfoDesign GmbH
http://www.merlin-zwo.de