Ruby - 计算数组的每个元素之间的返回值

时间:2011-08-14 20:19:48

标签: ruby

我必须计算数组的每个元素之间的回报

请看一下它的样本:

nav = ["100.00", "86.21", "84.65", "82.46", "86.94"]

这是我使用的循环:

0.upto(nav.count - 2) do |i|
  perf = (nav[i + 1].to_f / nav[i].to_f - 1) * 100
  p perf
end

它有效,但我的观点是关于数组的最后一个元素。

首先,我想使用类似的东西:

nav.length.times do 
  ... 
end

然后,我用了:

0.upto(nav.count - 2) 

为了避免计算(最后一个值+ 1),这将是零。

但是,我很高兴知道是否有更好的方法。

感谢您的建议。

3 个答案:

答案 0 :(得分:4)

nav.map(&:to_f).each_cons(2){|a,b| p (b/a-1)*100}
#=> -13.790000000000003
#=> -1.809534856745143
#=> -2.587123449497941
#=> 5.432937181663844
#=>  => nil

如果你需要返回一个值数组:

nav.map(&:to_f).each_cons(2).inject([]){|ar,(a,b)| ar << (b/a-1)*100}
#=> [-13.790000000000003, -1.809534856745143, -2.587123449497941, 5.432937181663844]
  

关于第二个例子:这种注入结构更好地称为“地图”;-) - @tokland

nav.map(&:to_f).each_cons(2).map{|a,b| (b/a-1)*100}

答案 1 :(得分:0)

您可能赞成Enumerable#inject

nav = ["100.00", "86.21", "84.65", "82.46", "86.94"]
i = 0
perf_array = nav.inject([]) do |result, elem|
  i = i + 1
  resultpush((nav[i].to_f / nav[i - 1].to_f - 1) * 100)
end

# Now perf_array contains each of your margins

编辑:实际上each_cons更好(哎呀!好吧,每天都要学习新东西):

nav = ["100.00", "86.21", "84.65", "82.46", "86.94"]
perf_array = []
nav.map(&:to_f).each_cons(2) { |a, b| perf_array.push(b/a - 1) * 100 }

答案 2 :(得分:0)

您应该使用inject方法。这可以让您了解它的工作原理:

irb> nav.inject { |a, b| puts "#{a}, #{b}"; b }
100.00, 86.21
86.21, 84.65
84.65, 82.46
82.46, 86.94

以下是使用inject代码的代码:

nav.inject do |a, b|
  perf = (b.to_f / a.to_f - 1) * 100
  p perf

  # return b, which will become the new a in the next iteration
  b
end