Это один из способов сделать это, предполагая, что массив отсортирован по времени, как показано на примере.
Код
def avg_of_squares(a)
a.chunk { |t,v| t[0,8] }.map { |t,v|
[t[0,8], v.reduce(0) { |tot,(_,x)| tot + x*x }/(v.size.to_f)] }
end
Если a
не были отсортированы, сортировать его на первый элемент:
a.sort_by(&:first)
Пример
a = [["00:54:08.349", 14],
["00:54:08.349", 13],
["00:54:08.449", 20],
["00:54:09.349", 15],
["00:54:09.628", 21],
["00:54:10.679", 13],
["00:54:10.839", 12]]
avg_of_squares(a)
#=> [["00:54:08", 255.0], ["00:54:09", 333.0], ["00:54:10", 156.5]]
Объяснение
шаги:
e = a.chunk { |t,v| t[0,8] }
#=> #<Enumerator: #<Enumerator::Generator:0x007fbaac08a2f0>:each>
Преобразование перечислителем в массив, чтобы увидеть его содержимое:
e.to_a
#=> [["00:54:08", [["00:54:08.349", 14], ["00:54:08.349", 13],
# ["00:54:08.449", 20]]],
# ["00:54:09", [["00:54:09.349", 15], ["00:54:09.628", 21]]],
# ["00:54:10", [["00:54:10.679", 13], ["00:54:10.839", 12]]]]
f = e.map
#=> #<Enumerator: #<Enumerator: #
# <Enumerator::Generator:0x007fbaac08a2f0>:each>:map>
f.to_a
# (same as for e)
Вы можете думать о f
как "соединение переписчиком".Пропускают первый элемент f
в блок и назначить блок-переменные:
t,v = f.next
#=> ["00:54:08", [["00:54:08.349", 14], ["00:54:08.349", 13],
# ["00:54:08.449", 20]]]
t
#=> "00:54:08"
v
#=> [["00:54:08.349", 14], ["00:54:08.349", 13], ["00:54:08.449", 20]]
g = v.reduce(0) { |tot,(_,x)|tot + x*x }/(v.size.to_f)
#=> 255.0
поэтому первый элемент f
отображается:
["00:54:08", 255.0]
Остальные расчеты выполняются аналогично.
Значит, вы хотите усреднить значения, соответствующие> 00: 54: 08.00, но <00: 54: 09.000? Почему это похоже на то, что вы усредняете, возводя квадрат своих значений перед их добавлением и делением на количество операндов? Разве это не должно быть (14 + 13 + 20)/3'? Какой у вас код до сих пор? – Beartech
Цель состоит в том, чтобы получить среднее значение в секунду для значений во входной таблице. В идеале, все значения от '00: 54: 07.501' до' 00: 54: 08.499', попадают в ведро в секунду для '00: 54: 08.000'. Это не только среднее значение, но операция выполняется для отдельных значений перед усреднением. Я использовал «квадрат», чтобы просто проиллюстрировать этот аспект. – user3206440