Robert Klemme
4/9/2005 7:07:00 AM
"Trans" <transfire@gmail.com> schrieb im Newsbeitrag
news:1113017766.220202.153150@f14g2000cwb.googlegroups.com...
> Thanks Robert.
>
> I agree about returning self. Since dup can't be used when the object
> is immutable (that's the condition isn't it?) then it would seem
> reasonable to return self.
Yeah, but in that case other applications can break because they think they
have a new instance while they have not. As I said, both approaches have
their merits - a classical dilemma. :-)
> I'm not sure what recursive structures you mean. And I don't see how it
> could work if the duping is left to the block. How could a new hash be
> built up then?
No, you need to create a new Hash instance. But you don't necessarily need
to dup keys and values. That's the dup I suggested to leave to the block.
> Hmm... perhaps it would work better if a hash parameter were fed into
> the block itself and then that could be used?
>
> h = h.traverse { |n,k,v| n[k.downcase] = v }
>
> Would that a better approach?
I wouldn't do that.
> BTW, somone sent me another version similar to my original, but using
> inject and somehow getting around the dup problem like so:
>
> def traverse(&b)
> inject({}) do |h,kv|
> k,v = kv.first.dup, kv.last.dup
> b[k,v]
> h[k] = (Hash === v ? v.traverse(&b) : v)
> h
> end
> end
That's not a solution for the dup problem, as "k,v = kv.first.dup,
kv.last.dup" will throw anyway.
If you really always need copies then the easiest might acutally be to use
Marshal and work on the copy. Marshal has solved all the problems of
recursion and duping already - so why do the work twice?
Kind regards
robert