@@ -286,6 +286,9 @@ pub struct TestOpts {
286
286
pub logfile : Option < Path > ,
287
287
pub nocapture : bool ,
288
288
pub color : ColorConfig ,
289
+ pub show_boxplot : bool ,
290
+ pub boxplot_width : uint ,
291
+ pub show_all_stats : bool ,
289
292
}
290
293
291
294
impl TestOpts {
@@ -303,6 +306,9 @@ impl TestOpts {
303
306
logfile : None ,
304
307
nocapture : false ,
305
308
color : AutoColor ,
309
+ show_boxplot : false ,
310
+ boxplot_width : 50 ,
311
+ show_all_stats : false ,
306
312
}
307
313
}
308
314
}
@@ -333,7 +339,10 @@ fn optgroups() -> Vec<getopts::OptGroup> {
333
339
getopts:: optopt( "" , "color" , "Configure coloring of output:
334
340
auto = colorize if stdout is a tty and tests are run on serially (default);
335
341
always = always colorize output;
336
- never = never colorize output;" , "auto|always|never" ) )
342
+ never = never colorize output;" , "auto|always|never" ) ,
343
+ getopts:: optflag( "" , "boxplot" , "Display a boxplot of the benchmark statistics" ) ,
344
+ getopts:: optopt( "" , "boxplot-width" , "Set the boxplot width (default 50)" , "WIDTH" ) ,
345
+ getopts:: optflag( "" , "stats" , "Display the benchmark min, max, and quartiles" ) )
337
346
}
338
347
339
348
fn usage ( binary : & str ) {
@@ -424,6 +433,21 @@ pub fn parse_opts(args: &[String]) -> Option<OptRes> {
424
433
v) ) ) ,
425
434
} ;
426
435
436
+ let show_boxplot = matches. opt_present ( "boxplot" ) ;
437
+ let boxplot_width = match matches. opt_str ( "boxplot-width" ) {
438
+ Some ( width) => {
439
+ match FromStr :: from_str ( width. as_slice ( ) ) {
440
+ Some ( width) => width,
441
+ None => {
442
+ return Some ( Err ( format ! ( "argument for --boxplot-width must be a uint" ) ) ) ;
443
+ }
444
+ }
445
+ }
446
+ None => 50 ,
447
+ } ;
448
+
449
+ let show_all_stats = matches. opt_present ( "stats" ) ;
450
+
427
451
let test_opts = TestOpts {
428
452
filter : filter,
429
453
run_ignored : run_ignored,
@@ -436,6 +460,9 @@ pub fn parse_opts(args: &[String]) -> Option<OptRes> {
436
460
logfile : logfile,
437
461
nocapture : nocapture,
438
462
color : color,
463
+ show_boxplot : show_boxplot,
464
+ boxplot_width : boxplot_width,
465
+ show_all_stats : show_all_stats,
439
466
} ;
440
467
441
468
Some ( Ok ( test_opts) )
@@ -486,6 +513,9 @@ struct ConsoleTestState<T> {
486
513
log_out : Option < File > ,
487
514
out : OutputLocation < T > ,
488
515
use_color : bool ,
516
+ show_boxplot : bool ,
517
+ boxplot_width : uint ,
518
+ show_all_stats : bool ,
489
519
total : uint ,
490
520
passed : uint ,
491
521
failed : uint ,
@@ -512,6 +542,9 @@ impl<T: Writer> ConsoleTestState<T> {
512
542
out : out,
513
543
log_out : log_out,
514
544
use_color : use_color ( opts) ,
545
+ show_boxplot : opts. show_boxplot ,
546
+ boxplot_width : opts. boxplot_width ,
547
+ show_all_stats : opts. show_all_stats ,
515
548
total : 0 u,
516
549
passed : 0 u,
517
550
failed : 0 u,
@@ -607,8 +640,31 @@ impl<T: Writer> ConsoleTestState<T> {
607
640
}
608
641
TrBench ( ref bs) => {
609
642
try!( self . write_bench ( ) ) ;
610
- self . write_plain ( format ! ( ": {}" ,
611
- fmt_bench_samples( bs) ) . as_slice ( ) )
643
+
644
+ if self . show_boxplot {
645
+ let mut wr = Vec :: new ( ) ;
646
+
647
+ try!( stats:: write_boxplot ( & mut wr, & bs. ns_iter_summ , self . boxplot_width ) ) ;
648
+
649
+ let s = String :: from_utf8 ( wr) . unwrap ( ) ;
650
+
651
+ try!( self . write_plain ( format ! ( ": {}" , s) . as_slice ( ) ) ) ;
652
+ }
653
+
654
+ if self . show_all_stats {
655
+ let mut wr = Vec :: new ( ) ;
656
+
657
+ try!( stats:: write_5_number_summary ( & mut wr, & bs. ns_iter_summ ) ) ;
658
+
659
+ let s = String :: from_utf8 ( wr) . unwrap ( ) ;
660
+
661
+ try!( self . write_plain ( format ! ( ": {}" , s) . as_slice ( ) ) ) ;
662
+ } else {
663
+ try!( self . write_plain ( format ! ( ": {}" ,
664
+ fmt_bench_samples( bs) ) . as_slice ( ) ) ) ;
665
+ }
666
+
667
+ Ok ( ( ) )
612
668
}
613
669
} ) ;
614
670
self . write_plain ( "\n " )
@@ -681,14 +737,14 @@ impl<T: Writer> ConsoleTestState<T> {
681
737
}
682
738
Improvement ( pct) => {
683
739
improved += 1 ;
684
- try!( self . write_plain ( format ! ( ": {}" , * k) . as_slice ( ) ) ) ;
740
+ try!( self . write_plain ( format ! ( ": {} " , * k) . as_slice ( ) ) ) ;
685
741
try!( self . write_improved ( ) ) ;
686
742
try!( self . write_plain ( format ! ( " by {:.2}%\n " ,
687
743
pct as f64 ) . as_slice ( ) ) ) ;
688
744
}
689
745
Regression ( pct) => {
690
746
regressed += 1 ;
691
- try!( self . write_plain ( format ! ( ": {}" , * k) . as_slice ( ) ) ) ;
747
+ try!( self . write_plain ( format ! ( ": {} " , * k) . as_slice ( ) ) ) ;
692
748
try!( self . write_regressed ( ) ) ;
693
749
try!( self . write_plain ( format ! ( " by {:.2}%\n " ,
694
750
pct as f64 ) . as_slice ( ) ) ) ;
@@ -860,6 +916,9 @@ fn should_sort_failures_before_printing_them() {
860
916
log_out : None ,
861
917
out : Raw ( Vec :: new ( ) ) ,
862
918
use_color : false ,
919
+ show_boxplot : false ,
920
+ boxplot_width : 0 ,
921
+ show_all_stats : false ,
863
922
total : 0 u,
864
923
passed : 0 u,
865
924
failed : 0 u,
0 commit comments