lib/benchmark_driver/repeater.rb in benchmark_driver-0.14.13 vs lib/benchmark_driver/repeater.rb in benchmark_driver-0.14.14
- old
+ new
@@ -1,27 +1,38 @@
+require 'benchmark_driver/struct'
+
module BenchmarkDriver
# Repeat calling block and return desired result: "best", "worst" or "average".
module Repeater
VALID_TYPES = %w[best worst average]
+ RepeatResult = ::BenchmarkDriver::Struct.new(
+ :value, # the value desired by --repeat-result
+ :all_values, # all benchmark results. Used by --output=all.
+ )
+
class << self
# `block.call` can return multiple objects, but the first one is used for sort.
# When `config.repeat_result == 'average'`, how to deal with rest objects is decided
# by `:rest_on_average` option.
+ #
+ # @param [Proc] block - returns Float or [Float, ...]
def with_repeat(config:, larger_better:, rest_on_average: :first, &block)
values = config.repeat_count.times.map { block.call }
- case config.repeat_result
- when 'best'
- best_result(values, larger_better)
- when 'worst'
- best_result(values, !larger_better)
- when 'average'
- average_result(values, rest_on_average)
- else
- raise "unexpected repeat_result #{config.repeat_result.inspect}"
- end
+ desired_value =
+ case config.repeat_result
+ when 'best'
+ best_result(values, larger_better)
+ when 'worst'
+ best_result(values, !larger_better)
+ when 'average'
+ average_result(values, rest_on_average)
+ else
+ raise "unexpected repeat_result #{config.repeat_result.inspect}"
+ end
+ RepeatResult.new(value: desired_value, all_values: extract_values(values))
end
private
def best_result(values, larger_better)
@@ -43,9 +54,15 @@
values.first.size.times.map do |index|
values.map { |v| v[index] }.inject(&:+) / values.first.size.to_f
end
else
raise "unexpected rest_on_average #{rest_on_average.inspect}"
+ end
+ end
+
+ def extract_values(values)
+ values.map do |value|
+ value.is_a?(Array) ? value.first : value
end
end
end
end
end