#!/usr/bin/perl $debug = 0; $detail = 0; $html = 0; $tex = 0; $extras = 0; $alt = 0; $usage = "Usage: mo-score [--detail] [--alt] [--extras] [--html] [--tex] ..."; while (($arg = $ARGV[0]) =~ /^--([a-z]+)$/) { shift @ARGV; $var = "\$$1"; if (!eval "defined $var") { die $usage; } eval "$var = 1;"; } @ARGV || die $usage; print STDERR "Scanning contestants... "; open (CT, "bin/mo-get-users --full |") || die "Cannot get list of contestants"; while () { chomp; ($u,$f) = split /\t/; ($u eq "somebody") && next; $users{$u}=$f; } close CT; print STDERR 0+keys %users, "\n"; print STDERR "Scanning exceptions... "; if ($extras && open (EX, "exceptions")) { while () { chomp; (/^$/ || /^#/) && next; @a = split /\s+/; $u = shift @a; defined $users{$u} || die "Unknown user $u"; while (@a) { $extra{$u} += shift @a; } } close EX; print STDERR "OK\n"; } else { print STDERR "none\n"; } print STDERR "Scanning task results... "; $need_tasks = join("|", @ARGV); foreach $u (keys %users) { opendir (D, "testing/$u") or next; foreach $t (readdir(D)) { $t =~ /^\./ && next; $t =~ /$need_tasks/ || next; $known_tasks{$t} = 1; $tt = "testing/$u/$t/points" . ($alt ? ".alt" : ""); -f $tt || next; print STDERR "$u/$t "; open (X, $tt) || die "Unable to open $tt"; while () { chomp; /^(\S+) (-?\d+)\s*(.*)/ || die "Parse error: $_"; $ttest = $1; $tpts = $2; $trem = $3; $known_tests{$t}{$ttest} = 1; $results{$u}{$t}{$ttest} = $tpts; $remarks{$u}{$t}{$ttest} = $trem; $cmt = $tpts; if ($tpts == 0) { if ($trem =~ /^Compile /) { $cmt = "CE"; } elsif ($trem =~ /^Time limit exceeded/) { $cmt = "TO"; } elsif ($trem =~ /^Exited with error /) { $cmt = "RE"; } elsif ($trem =~ /^Caught fatal signal /) { $cmt = "SG"; } elsif ($trem =~ /^([A-Za-z])\S*\s+([A-Za-z])/) { ($cmt = "$1$2") =~ tr/a-z/A-Z/; } elsif ($trem =~ /^Wrong answer/) { $cmt = "WA"; } } $comment{$u}{$t}{$ttest} = $cmt; $total{$u}{$t} += $tpts; } close X; } closedir D; } print STDERR "OK\n"; print STDERR "Creating table template... "; @header = ("Rank","User","Name"); @body = ('','$u','$users{$u}'); @bodysums = (); @footer = ('"Total"','',''); if (keys %extra) { push @header, "Extra"; push @body, '$extra{$u}'; $col = 0+@footer; push @bodysums, $col; push @footer, "sum($col)"; } foreach $t (@ARGV) { defined $known_tasks{$t} || die "Unknown task $t"; push @header, substr($t, 0, 4); push @body, "(\$xx = \$total{\$u}{'$t'}) > 0 ? \$xx : 0"; $col = 0+@footer; push @footer, "sum($col)"; push @bodysums, $col; if ($detail) { foreach $s (sort { $a <=> $b } keys %{$known_tests{$t}}) { push @header, "$s"; push @body, "\$comment{\$u}{'$t'}{'$s'}"; $col = 0+@footer; push @footer, "sum($col)"; } } } push @header, "Total"; push @body, join('+', map { $_ = "\$$_" } @bodysums); $col = 0+@footer; push @footer, "sum($col)"; print STDERR "OK\n"; print STDERR "h: ", join(':',@header), "\n" if $debug; print STDERR "b: ", join(':',@body), "\n" if $debug; print STDERR "f: ", join(':',@footer), "\n" if $debug; print STDERR "Filling in results... "; @table = (); foreach $u (keys %users) { $row = []; foreach my $c (@body) { $c =~ s/\$(\d+)/\$\$row[$1]/g; $x = eval $c; push @$row, (defined $x ? $x : '-'); } print STDERR "row: ", join(':',@$row), "\n" if $debug; push @table, $row; } print STDERR "OK\n"; print STDERR "Sorting... "; $sortcol = @{$table[0]} - 1; $namecol = 2; @table = sort { my $p, $an, $bn; $p = $$b[$sortcol] <=> $$a[$sortcol]; ($an = $$a[$namecol]) =~ s/(\S+)\s+(\S+)/$2 $1/; ($bn = $$b[$namecol]) =~ s/(\S+)\s+(\S+)/$2 $1/; $p ? $p : ($an cmp $bn); } @table; $i=0; while ($i < @table) { $j = $i; while ($i < @table && ${$table[$i]}[$sortcol] == ${$table[$j]}[$sortcol]) { $i++; } if ($i == $j+1) { ${table[$j]}[0] = "$i."; } else { ${table[$j]}[0] = $j+1 . ".-" . $i . "."; $j++; while ($j < $i) { ${table[$j++]}[0] = ""; }; } } print STDERR "OK\n"; print STDERR "Attaching headers and footers... "; sub sum { my $col=shift @_; my $t=0; foreach my $z (0..@table-1) { $t += ${$table[$z]}[$col]; } $t; } map { $_ = eval $_; } @footer; push @table, \@footer; unshift @table, \@header; print STDERR "OK\n"; if ($debug) { foreach $r (@table) { print join(':',@$r), "\n"; } } elsif ($html) { print '', "\n"; print "Rank list\n"; print "

Rank list

\n"; print "\n"; $hdr = 1; foreach $r (@table) { print "", join('',map { if ($hdr) { $_ = "
$_"; } else { $_ = " 14 ? " width=150" : "") . ">$_"; } } @$r), "\n"; $hdr = 0; } print "
\n"; print "\n"; } elsif ($tex) { print "\\error{TeX output not supported yet!}\n"; } else { foreach $r (@table) { print join("\t",@$r), "\n"; } }