1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163
|
require 'minitest/spec'
require 'benchmark'
MiniTest::Unit.autorun
describe Benchmark do
BENCH_FOR_TIMES_UPTO = lambda do |x|
n = 1000
tf = x.report("for:") { for _ in 1..n; '1'; end }
tt = x.report("times:") { n.times do ; '1'; end }
tu = x.report("upto:") { 1.upto(n) do ; '1'; end }
[tf+tt+tu, (tf+tt+tu)/3]
end
BENCH_FOR_TIMES_UPTO_NO_LABEL = lambda do |x|
n = 1000
x.report { for _ in 1..n; '1'; end }
x.report { n.times do ; '1'; end }
x.report { 1.upto(n) do ; '1'; end }
end
LABELS = %w[first second third]
def bench(type = :bm, *args, &block)
if block
Benchmark.send(type, *args, &block)
else
Benchmark.send(type, *args) do |x|
LABELS.each { |label|
x.report(label) {}
}
end
end
end
def capture_output
capture_io { yield }.first.gsub(/[ \-]\d\.\d{6}/, ' --time--')
end
def capture_bench_output(type, *args, &block)
capture_output { bench(type, *args, &block) }
end
describe 'Tms' do
it 'outputs nicely' do
Benchmark::Tms.new.to_s.must_equal " 0.000000 0.000000 0.000000 ( 0.000000)\n"
Benchmark::Tms.new(1,2,3,4,5).to_s.must_equal " 1.000000 2.000000 10.000000 ( 5.000000)\n"
Benchmark::Tms.new(1,2,3,4,5,'label').format('%u %y %U %Y %t %r %n').must_equal \
"1.000000 2.000000 3.000000 4.000000 10.000000 (5.000000) label"
Benchmark::Tms.new(1).format('%u %.3f', 2).must_equal "1.000000 2.000"
Benchmark::Tms.new(100, 150, 0, 0, 200).to_s.must_equal \
"100.000000 150.000000 250.000000 (200.000000)\n"
end
it 'wont modify the format String given' do
format = "format %u"
Benchmark::Tms.new.format(format)
format.must_equal "format %u"
end
end
describe 'benchmark' do
it 'makes extra calcultations with an Array at the end of the benchmark and show the result' do
capture_bench_output(:benchmark,
Benchmark::CAPTION, 7,
Benchmark::FORMAT, ">total:", ">avg:",
&BENCH_FOR_TIMES_UPTO).must_equal BENCHMARK_OUTPUT_WITH_TOTAL_AVG
end
end
describe 'bm' do
it "returns an Array of the times with the labels" do
[:bm, :bmbm].each do |meth|
capture_io do
results = bench(meth)
results.must_be_instance_of Array
results.size.must_equal LABELS.size
results.zip(LABELS).each { |tms, label|
tms.must_be_instance_of Benchmark::Tms
tms.label.must_equal label
}
end
end
end
it 'correctly output when the label width is given' do
capture_bench_output(:bm, 6).must_equal BM_OUTPUT
end
it 'correctly output when no label is given' do
capture_bench_output(:bm, &BENCH_FOR_TIMES_UPTO_NO_LABEL).must_equal BM_OUTPUT_NO_LABEL
end
it 'can make extra calcultations with an array at the end of the benchmark' do
capture_bench_output(:bm, 7, ">total:", ">avg:",
&BENCH_FOR_TIMES_UPTO).must_equal BENCHMARK_OUTPUT_WITH_TOTAL_AVG
end
end
describe 'bmbm' do
it 'correctly guess the label width even when not given' do
capture_bench_output(:bmbm).must_equal BMBM_OUTPUT
end
it 'correctly output when the label width is given (bmbm ignore it, but it is a frequent mistake)' do
capture_bench_output(:bmbm, 6).must_equal BMBM_OUTPUT
end
end
describe 'Report' do
describe '#item' do
it 'shows the title, even if not a string' do
capture_bench_output(:bm) { |x| x.report(:title) {} }.must_include 'title'
capture_bench_output(:bmbm) { |x| x.report(:title) {} }.must_include 'title'
end
end
end
describe 'Bugs' do
it '[ruby-dev:40906] can add in-place the time of execution of the block given' do
t = Benchmark::Tms.new
t.real.must_equal 0
t.add! { sleep 0.1 }
t.real.wont_equal 0
end
end
end
BM_OUTPUT = <<BENCH
user system total real
first --time-- --time-- --time-- ( --time--)
second --time-- --time-- --time-- ( --time--)
third --time-- --time-- --time-- ( --time--)
BENCH
BM_OUTPUT_NO_LABEL = <<BENCH
user system total real
--time-- --time-- --time-- ( --time--)
--time-- --time-- --time-- ( --time--)
--time-- --time-- --time-- ( --time--)
BENCH
BMBM_OUTPUT = <<BENCH
Rehearsal ------------------------------------------
first --time-- --time-- --time-- ( --time--)
second --time-- --time-- --time-- ( --time--)
third --time-- --time-- --time-- ( --time--)
--------------------------------- total: --time--sec
user system total real
first --time-- --time-- --time-- ( --time--)
second --time-- --time-- --time-- ( --time--)
third --time-- --time-- --time-- ( --time--)
BENCH
BENCHMARK_OUTPUT_WITH_TOTAL_AVG = <<BENCH
user system total real
for: --time-- --time-- --time-- ( --time--)
times: --time-- --time-- --time-- ( --time--)
upto: --time-- --time-- --time-- ( --time--)
>total: --time-- --time-- --time-- ( --time--)
>avg: --time-- --time-- --time-- ( --time--)
BENCH
|