如何用哈希值对数组求和

我有以下带哈希的数组:

[ [ {"created_at":"2013-11-16","position_f":1}, {"created_at":"2013-11-17","position_f":3}, {"created_at":"2013-11-18","position_f":0}, {"created_at":"2013-11-19","position_f":1} ], [ {"created_at":"2013-11-16","position_f":2}, {"created_at":"2013-11-17","position_f":3}, {"created_at":"2013-11-18","position_f":11}, {"created_at":"2013-11-19","position_f":45} ] ] 

预期结果:

  [ {"created_at":"2013-11-16","position_f":3}, {"created_at":"2013-11-17","position_f":6}, {"created_at":"2013-11-18","position_f":11}, {"created_at":"2013-11-19","position_f":46} ] 

什么是用散列对这些数组求​​和并在Expected result下得到结果的简单方法

谢谢。

这里是 :

 arr =[ [ {"created_at"=>"2013-11-16","position_f"=>10}, {"created_at"=>"2013-11-17","position_f"=>0}, {"created_at"=>"2013-11-18","position_f"=>0}, {"created_at"=>"2013-11-19","position_f"=>1} ], [ {"created_at"=>"2013-11-16","position_f"=>20}, {"created_at"=>"2013-11-17","position_f"=>0}, {"created_at"=>"2013-11-18","position_f"=>11}, {"created_at"=>"2013-11-19","position_f"=>45} ] ] p arr.inject(0){|sum,a| sum +=a[0]["position_f"]} # => 30 

使用awesome_print更新

 require 'awesome_print' arr = [ [ {"created_at"=>"2013-11-16","position_f"=>1}, {"created_at"=>"2013-11-17","position_f"=>3}, {"created_at"=>"2013-11-18","position_f"=>0}, {"created_at"=>"2013-11-19","position_f"=>1} ], [ {"created_at"=>"2013-11-16","position_f"=>2}, {"created_at"=>"2013-11-17","position_f"=>3}, {"created_at"=>"2013-11-18","position_f"=>11}, {"created_at"=>"2013-11-19","position_f"=>45} ] ] nwar = arr.flatten.group_by{|h| h['created_at']}.map do |k,v| {"created_at" => k,"position_f" => v.reduce(0){|sum,h| sum += h['position_f']}} end ap nwar,:index => false 

输出:

 [ { "created_at" => "2013-11-16", "position_f" => 3 }, { "created_at" => "2013-11-17", "position_f" => 6 }, { "created_at" => "2013-11-18", "position_f" => 11 }, { "created_at" => "2013-11-19", "position_f" => 46 } ] 

假设您想要对所有数组中的所有position_f值求和,我会这样做:

 sum = 0 outer_array.each do |inner_array| inner_array.each do |inner_hash| sum += inner_hash['position_f'] end end 

我想这就是你想要的:

 data = [ [ {"created_at"=>"2013-11-16","position_f"=>0}, {"created_at"=>"2013-11-17","position_f"=>0}, {"created_at"=>"2013-11-18","position_f"=>0}, {"created_at"=>"2013-11-19","position_f"=>1} ], [ {"created_at"=>"2013-11-16","position_f"=>0}, {"created_at"=>"2013-11-17","position_f"=>0}, {"created_at"=>"2013-11-18","position_f"=>11}, {"created_at"=>"2013-11-19","position_f"=>45} ] ] @hash = Hash.new(0) data.each do |arr_of_hashes| arr_of_hashes.each_with_object(@hash) {|arr_hash, master_hash| master_hash[arr_hash["created_at"]] += arr_hash["position_f"]} end @hash 

这是IRB的运行:

 1.9.3p448 :020 > data = [ 1.9.3p448 :021 > [ 1.9.3p448 :022 > {"created_at"=>"2013-11-16","position_f"=>0}, 1.9.3p448 :023 > {"created_at"=>"2013-11-17","position_f"=>0}, 1.9.3p448 :024 > {"created_at"=>"2013-11-18","position_f"=>0}, 1.9.3p448 :025 > {"created_at"=>"2013-11-19","position_f"=>1} 1.9.3p448 :026?> ], 1.9.3p448 :027 > [ 1.9.3p448 :028 > {"created_at"=>"2013-11-16","position_f"=>0}, 1.9.3p448 :029 > {"created_at"=>"2013-11-17","position_f"=>0}, 1.9.3p448 :030 > {"created_at"=>"2013-11-18","position_f"=>11}, 1.9.3p448 :031 > {"created_at"=>"2013-11-19","position_f"=>45} 1.9.3p448 :032?> ] 1.9.3p448 :033?> ] => [[{"created_at"=>"2013-11-16", "position_f"=>0}, {"created_at"=>"2013-11-17", "position_f"=>0}, {"created_at"=>"2013-11-18", "position_f"=>0}, {"created_at"=>"2013-11-19", "position_f"=>1}], [{"created_at"=>"2013-11-16", "position_f"=>0}, {"created_at"=>"2013-11-17", "position_f"=>0}, {"created_at"=>"2013-11-18", "position_f"=>11}, {"created_at"=>"2013-11-19", "position_f"=>45}]] 1.9.3p448 :034 > 1.9.3p448 :035 > @hash = Hash.new(0) => {} 1.9.3p448 :036 > 1.9.3p448 :037 > data.each do |arr_of_hashes| 1.9.3p448 :038 > arr_of_hashes.each_with_object(@hash) {|arr_hash, master_hash| master_hash[arr_hash["created_at"]] += arr_hash["position_f"]} 1.9.3p448 :039?> end => [[{"created_at"=>"2013-11-16", "position_f"=>0}, {"created_at"=>"2013-11-17", "position_f"=>0}, {"created_at"=>"2013-11-18", "position_f"=>0}, {"created_at"=>"2013-11-19", "position_f"=>1}], [{"created_at"=>"2013-11-16", "position_f"=>0}, {"created_at"=>"2013-11-17", "position_f"=>0}, {"created_at"=>"2013-11-18", "position_f"=>11}, {"created_at"=>"2013-11-19", "position_f"=>45}]] 1.9.3p448 :040 > 1.9.3p448 :041 > @hash => {"2013-11-16"=>0, "2013-11-17"=>0, "2013-11-18"=>11, "2013-11-19"=>46} 

然后,如果你想要总数,你可以这样做:

 1.9.3p448 :081 > @hash.values.sum => 57 
 result = data.flatten.group_by{|x|x[:created_at]}.map do |x| val = x.first sum = x.last.map{|x| x[:position_f]}.inject(:+) {created_at: val, position_f: sum} end p result #=> [{:created_at=>"2013-11-16", :position_f=>0}, {:created_at=>"2013-11-17", :position_f=>0}, {:created_at=>"2013-11-18", :position_f=>11}, {:created_at=>"2013-11-19", :position_f=>46}] 

或者,如果您不关心最终演示:

 result = data.flatten.each_with_object(Hash.new(0)) do |item,hash| hash[item[:created_at]] += item[:position_f] end p result #=> {"2013-11-16"=>0, "2013-11-17"=>0, "2013-11-18"=>11, "2013-11-19"=>46}