Compare commits

...

10 Commits

2 changed files with 46 additions and 44 deletions

View File

@ -3,13 +3,14 @@ use v5.32;
use HTML::TableExtract; use HTML::TableExtract;
use File::Slurp; use File::Slurp;
use Data::Dumper; use Data::Dumper;
use List::Util qw(sum);
use Text::SimpleTable::AutoWidth; use Text::SimpleTable::AutoWidth;
use WWW::Mechanize (); use WWW::Mechanize ();
use List::AllUtils qw/ sum pairmap /;
use List::UtilsBy qw/ nsort_by partition_by /;
use experimental qw/ signatures /; use experimental qw/ signatures /;
unless(caller) { unless (caller) {
my $ts = get_mersenne_results(); my $ts = get_mersenne_results();
generate_output_table($ts)->draw; generate_output_table($ts)->draw;
@ -22,8 +23,12 @@ sub get_mersenne_results() {
my $mech = WWW::Mechanize->new; my $mech = WWW::Mechanize->new;
my $url = my $url = join '?', 'https://www.mersenne.org/results/',
'https://www.mersenne.org/results/?extf=1&exp1=1&execm=1&excert=1&exp_lo=2&exp_hi=&limit=10000'; join '&',
pairmap { join '=', $a, $b }
exp_lo => 2,
limit => 10_000,
map { $_ => 1 } qw/ extf exp1 execm excert /;
$mech->get($url); $mech->get($url);
@ -40,53 +45,38 @@ sub get_mersenne_results() {
return extract_first_table($html_string); return extract_first_table($html_string);
} }
sub extract_first_table($html) { sub extract_first_table ($html) {
$html =~ s/\n//g; return HTML::TableExtract
->new( depth => 0, count => 2 )
my $te = HTML::TableExtract->new( depth => 0, count => 2 ); ->parse( $html =~ s/\n//gr )
->first_table_found;
$te->parse($html);
return $te->first_table_found;
} }
sub generate_output_table ($ts) { sub generate_output_table ($ts) {
# group GHZ Days results by computer, compute GHZ Days per Day (GHZ Days / Days)
my $list;
foreach my $row ( $ts->rows ) {
foreach my $cell ($row) {
my $machine = @$cell[0];
my $ghz_days = @$cell[6];
$ghz_days =~ s/\s//g;
my $days = @$cell[4];
$days =~ s/\s//g;
if ( $days > 0 ) {
my $perf = $ghz_days / $days;
push( @{ $list->{$machine} }, $perf );
}
}
}
# create hash with each comptuer and its average GHz Days per day
my %ranks;
foreach my $key ( keys %$list ) {
my $mean = sum( @{ $list->{$key} } ) / @{ $list->{$key} };
my $rounded = int( $mean + 0.5 );
$ranks{$key} = $rounded;
}
# sort hash by the average and print to screen
my $tbl = Text::SimpleTable::AutoWidth->new( my $tbl = Text::SimpleTable::AutoWidth->new(
captions => [qw/ Computer GHZDaysPerDay /] ); captions => [qw/ Computer GHZDaysPerDay /] );
foreach # group GHZ Days results by computer, compute GHZ Days per Day (GHZ Days / Days)
my $key ( reverse sort { $ranks{$a} <=> $ranks{$b} } keys(%ranks) ) { $tbl->row(@$_) for
$tbl->row( $key, $ranks{$key} ); reverse
nsort_by { $_->[1] }
pairmap { [ $a, $b ] } # group for the sorting
pairmap { $a => sprintf "%.0f", sum(@$b) / @$b } # take the mean
pairmap {
# calculate our stats
$a => [ map { $_->{ghz_days} / $_->{days} } @$b ]
} }
partition_by { $_->{machine} } # group by machine
grep { $_->{days} > 0 } # skip entries with no days
map { # get the info
my $machine = $_->[0];
my $days = $_->[4] =~ s/\s//gr;
my $ghz_days = $_->[6] =~ s/\s//gr;
+{ days => $days, ghz_days => $ghz_days, machine => $machine }
}
$ts->rows;
return $tbl; return $tbl;
} }

12
t/basic.t Normal file
View File

@ -0,0 +1,12 @@
use v5.32.0;
use Test2::V0;
use Path::Tiny;
require './script.pl';
my $input = path('./sample.html')->slurp;
like generate_output_table( extract_first_table($input) )->draw => qr/lonestar/;
done_testing();