@@ -7,7 +7,8 @@ gcscrub() = (GC.gc(); GC.gc(); GC.gc(); GC.gc())
7
7
# Benchmark #
8
8
# ############
9
9
10
- mutable struct Benchmark{id}
10
+ mutable struct Benchmark
11
+ samplefunc
11
12
params:: Parameters
12
13
end
13
14
87
88
# Note that trials executed via `run` and `lineartrial` are always executed at top-level
88
89
# scope, in order to allow transfer of locally-scoped variables into benchmark scope.
89
90
90
- # these stubs get overloaded by @benchmarkable
91
- function sample end
92
- function _run end
91
+ function _run (b:: Benchmark , p:: Parameters ; verbose = false , pad = " " , kwargs... )
92
+ params = Parameters (p; kwargs... )
93
+ @assert params. seconds > 0.0 " time limit must be greater than 0.0"
94
+ params. gctrial && gcscrub ()
95
+ start_time = Base. time ()
96
+ trial = Trial (params)
97
+ params. gcsample && gcscrub ()
98
+ s = b. samplefunc (params)
99
+ push! (trial, s[1 : end - 1 ]. .. )
100
+ return_val = s[end ]
101
+ iters = 2
102
+ while (Base. time () - start_time) < params. seconds && iters ≤ params. samples
103
+ params. gcsample && gcscrub ()
104
+ push! (trial, b. samplefunc (params)[1 : end - 1 ]. .. )
105
+ iters += 1
106
+ end
107
+ return sort! (trial), return_val
108
+ end
93
109
94
110
Base. run (b:: Benchmark , p:: Parameters = b. params; progressid= nothing , nleaves= NaN , ndone= NaN , kwargs... ) =
95
111
run_result (b, p; kwargs... )[1 ]
@@ -130,7 +146,7 @@ function _lineartrial(b::Benchmark, p::Parameters = b.params; maxevals = RESOLUT
130
146
for evals in eachindex (estimates)
131
147
params. gcsample && gcscrub ()
132
148
params. evals = evals
133
- estimates[evals] = first (sample (b, params))
149
+ estimates[evals] = first (b . samplefunc ( params))
134
150
completed += 1
135
151
((time () - start_time) > params. seconds) && break
136
152
end
216
232
# ############################
217
233
218
234
function prunekwargs (args... )
235
+ @nospecialize
219
236
firstarg = first (args)
220
237
if isa (firstarg, Expr) && firstarg. head == :parameters
221
238
return prunekwargs (drop (args, 1 )... , firstarg. args... )
@@ -291,6 +308,7 @@ macro benchmark(args...)
291
308
end
292
309
293
310
function benchmarkable_parts (args)
311
+ @nospecialize
294
312
core, params = prunekwargs (args... )
295
313
296
314
# extract setup/teardown if present, removing them from the original expression
@@ -321,22 +339,23 @@ end
321
339
322
340
macro benchmarkable (args... )
323
341
core, setup, teardown, params = benchmarkable_parts (args)
342
+ map! (esc, params, params)
324
343
325
344
# extract any variable bindings shared between the core and setup expressions
326
345
setup_vars = isa (setup, Expr) ? collectvars (setup) : []
327
346
core_vars = isa (core, Expr) ? collectvars (core) : []
328
347
out_vars = filter (var -> var in setup_vars, core_vars)
329
348
330
349
# generate the benchmark definition
331
- return esc ( quote
332
- $ BenchmarkTools . generate_benchmark_definition ($ __module__,
333
- $ (Expr (:quote , out_vars)),
334
- $ (Expr (:quote , setup_vars)),
335
- $ ( Expr (:quote , core)),
336
- $ ( Expr (:quote , setup)),
337
- $ ( Expr (:quote , teardown)),
338
- $ Parameters ($ (params... )))
339
- end )
350
+ return quote
351
+ generate_benchmark_definition ($ __module__,
352
+ $ (Expr (:quote , out_vars)),
353
+ $ (Expr (:quote , setup_vars)),
354
+ $ ( esc ( Expr (:quote , core) )),
355
+ $ ( esc ( Expr (:quote , setup) )),
356
+ $ ( esc ( Expr (:quote , teardown) )),
357
+ Parameters ($ (params... )))
358
+ end
340
359
end
341
360
342
361
# `eval` an expression that forcibly defines the specified benchmark at
347
366
# possible for them to conflict with names used in the setup or teardown expressions.
348
367
# A more robust solution would be preferable.
349
368
function generate_benchmark_definition (eval_module, out_vars, setup_vars, core, setup, teardown, params)
350
- id = Expr ( :quote , gensym ( " benchmark " ))
369
+ @nospecialize
351
370
corefunc = gensym (" core" )
352
371
samplefunc = gensym (" sample" )
353
372
type_vars = [gensym () for i in 1 : length (setup_vars)]
@@ -389,31 +408,7 @@ function generate_benchmark_definition(eval_module, out_vars, setup_vars, core,
389
408
__evals))
390
409
return __time, __gctime, __memory, __allocs, __return_val
391
410
end
392
- function $BenchmarkTools. sample (b:: $BenchmarkTools.Benchmark{$(id)} ,
393
- p:: $BenchmarkTools.Parameters = b. params)
394
- return $ (samplefunc)(p)
395
- end
396
- function $BenchmarkTools. _run (b:: $BenchmarkTools.Benchmark{$(id)} ,
397
- p:: $BenchmarkTools.Parameters ;
398
- verbose = false , pad = " " , kwargs... )
399
- params = $ BenchmarkTools. Parameters (p; kwargs... )
400
- @assert params. seconds > 0.0 " time limit must be greater than 0.0"
401
- params. gctrial && $ BenchmarkTools. gcscrub ()
402
- start_time = Base. time ()
403
- trial = $ BenchmarkTools. Trial (params)
404
- params. gcsample && $ BenchmarkTools. gcscrub ()
405
- s = $ (samplefunc)(params)
406
- push! (trial, s[1 : end - 1 ]. .. )
407
- return_val = s[end ]
408
- iters = 2
409
- while (Base. time () - start_time) < params. seconds && iters ≤ params. samples
410
- params. gcsample && $ BenchmarkTools. gcscrub ()
411
- push! (trial, $ (samplefunc)(params)[1 : end - 1 ]. .. )
412
- iters += 1
413
- end
414
- return sort! (trial), return_val
415
- end
416
- $ BenchmarkTools. Benchmark {$(id)} ($ (params))
411
+ $ BenchmarkTools. Benchmark ($ (samplefunc), $ (params))
417
412
end )
418
413
end
419
414
0 commit comments