开发者

ruby hash with self referencing elements / recursive hash

开发者 https://www.devze.com 2022-12-13 05:27 出处:网络
I need a ruby hash H with keys :a, :b, :c so that H[:b] = H[:a] + 1; H[:c] = H[:b] + 2 etc. How can I define such a hash in a one line declaration, like H = {:a=>1, :b => H[:a] + 1, :c => H[:b] +2, .

I need a ruby hash H with keys :a, :b, :c so that H[:b] = H[:a] + 1; H[:c] = H[:b] + 2 etc.

How can I define such a hash in a one line declaration, like H = {:a=>1, :b => H[:a] + 1, :c => H[:b] +2, ... } ?

I need something similar to DataMapper properties declaration:

property :path, FilePath

property :md5sum, String, :default => lambda { |r, p| Digest::MD5.hexdigest(r.path.read)}

w开发者_开发问答here :md5sum default value is referencing the :path property


This is the best I can do:

arr = [[:a,1], [:b,1], [:c,2]]; H = {:temp => 0}
arr.inject(:temp) { |last, kv| H[kv[0]] = H[last] + kv[1]; kv[0] }
H.delete :temp

Pretty ugly, and it isn't so obvious what it does. I suggest you just do it the straightforward way, unless it's really that much of a problem.


It's not clear what you are trying to accomplish. Note that hashes can have a default proc. Ex:

require 'digest/md5'
h = Hash.new do |hash, key|
  hash[:md5sum] = Digest::MD5.hexdigest(hash[:path]) if key == :md5sum
end

h[:path] = "/starway/to/heaven"
h[:md5sum]  # ==> "0e4faf226dac83569bde4fcf5bcd7ad6"
h[:md5sum] = "xyz"
h[:md5sum]  # ==> "xyz"


It sounds like you may want lazy declarations: http://moonbase.rydia.net/software/lazy.rb/

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号