简体   繁体   English

红宝石:求和两个或多个数组的对应成员

[英]ruby: sum corresponding members of two or more arrays

I've got two (or more) arrays with 12 integers in each (corresponding to values for each month). 我有两个(或更多)数组,每个数组中有12个整数(对应于每个月的值)。 All I want is to add them together so that I've got a single array with summed values for each month. 我想要的就是将它们加在一起,这样我就得到了一个包含每个月总值的单个数组。 Here's an example with three values: [1,2,3] and [4,5,6] => [5,7,9] 这是一个具有三个值的示例:[1,2,3]和[4,5,6] => [5,7,9]

The best I could come up with was: 我能想到的最好的是:

[[1,2,3],[4,5,6]].transpose.map{|arr| arr.inject{|sum, element| sum+element}} #=> [5,7,9]

Is there a better way of doing this? 有更好的方法吗? It just seems such a basic thing to want to do. 似乎想做的一件基本的事情。

Here's the transpose version Anurag suggested: 这是Anurag建议的transpose版本:

[[1,2,3], [4,5,6]].transpose.map {|x| x.reduce(:+)}

This will work with any number of component arrays. 这将适用于任何数量的组件阵列。 reduce and inject are synonyms, but reduce seems to me to more clearly communicate the code's intent here... reduceinject是同义词,但在我看来reduce可以在此处更清楚地传达代码的意图...

For clearer syntax (not the fastest), you can make use of Vector : 为了获得更清晰的语法(不是最快的语法),可以使用Vector

require 'matrix'
Vector[1,2,3] + Vector[4,5,6]
=> Vector[5, 7, 9]

For multiple vectors, you can do: 对于多个向量,您可以执行以下操作:

arr = [ Vector[1,2,3], Vector[4,5,6], Vector[7,8,9] ]
arr.inject(&:+)
=> Vector[12, 15, 18]

If you wish to load your arrays into Vectors and sum: 如果您希望将数组加载到Vector中并求和:

arrays = [ [1,2,3], [4,5,6], [7,8,9] ]
arrays.map { |a| Vector[*a] }.inject(:+)
=> Vector[12, 15, 18]

here's my attempt at code-golfing this thing: 这是我尝试对此事物进行代码搜索的尝试:

// ruby 1.9 syntax, too bad they didn't add a sum() function afaik
[1,2,3].zip([4,5,6]).map {|a| a.inject(:+)} # [5,7,9]

zip returns [1,4] , [2,5] , [3,6] , and map sums each sub-array. zip返回[1,4][2,5][3,6] ,并且map对每个子数组求和。

I humbly feel that the other answers I see are so complex that they would be confusing to code reviewers. 我谦卑地感到,我看到的其他答案是如此复杂,以至于会使代码审查者感到困惑。 You would need to add an explanatory comment, which just increases the amount of text needed. 您将需要添加一个解释性注释,这只会增加所需的文本量。

How about this instead: 怎么样呢:

a_arr = [1,2,3]
b_arr = [4,5,6]
(0..2).map{ |i| a_arr[i] + b_arr[i] }

Slightly different solution: (so that you're not hard coding the "2") 略有不同的解决方案:(这样您就不必对“ 2”进行硬编码了)

a_arr = [1,2,3]
b_arr = [4,5,6]
c_arr = []
a_arr.each_index { |i| c_arr[i] = a_arr[i] + b_arr[i] }

Finally, mathematically speaking, this is the same question as this: 最后,从数学上讲,这是与此相同的问题:

How do I perform vector addition in Ruby? 如何在Ruby中执行向量加法?

[[1,2,3],[4,5,6]].transpose.map{|a| a.sum} #=> [5,7,9]

Now we can use sum in 2.4 现在我们可以在2.4中使用sum

nums = [[1, 2, 3], [4, 5, 6]]
nums.transpose.map(&:sum) #=> [5, 7, 9]

@FriendFX, you are correct about @user2061694 answer. @FriendFX,您对@ user2061694的回答是正确的。 It only worked in Rails environment for me. 它只对我在Rails环境中有效。 You can make it run in plain Ruby if you make the following changes... 如果进行以下更改,则可以使其在纯Ruby中运行...

In the IRB 在IRB

[[0, 0, 0], [2, 2, 1], [1,3,4]].transpose.map {|a| a.inject(:+)}
 => [3, 5, 5]


[[1,2,3],[4,5,6]].transpose.map {|a| a.inject(:+)}
 => [5, 7, 9]

For: 对于:

a = [1,2,3]
b = [4,5,6]

You could zip and then use reduce : 您可以zip然后使用reduce

p a.zip(b).map{|v| v.reduce(:+) }
#=> [5, 7, 9]

Or, if you're sure that array a and b will always be of equal length: 或者,如果您确定数组ab的长度将始终相等:

p a.map.with_index { |v, i| v + b[i] }
#=> [5, 7, 9]

This might not be the best answer but it works. 这可能不是最佳答案,但它可以工作。

array_one = [1,2,3]
array_two = [4,5,6]
x = 0
array_three = []
while x < array_one.length
  array_three[x] = array_one[x] + array_two[x]
  x += 1
end

=>[5,7,9]

This might be more lines of code than other answers, but it is an answer nonetheless 与其他答案相比,这可能是更多的代码行,但这仍然是一个答案

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM