#!/usr/bin/env raku
# sort jobs depending on the current-time/priority/submit-time
sub schedule(@str_jobs) {
my %result;
my $time = 0;
my @jobs = @str_jobs.map: { %(<title submit duration priority> Z=> .split(',')) };
my $bag = @jobs.map({.<priority>}).Bag;
while $_ = @jobs.min(:p, { $^a<submit> <=> $time, -$^a<priority>, $^a<submit> }).head {
my $j = @jobs[.key]:delete;
$time = $j<submit> if $time < $j<submit>; # skip time
my $ends = $time + $j<duration>;
my $wait = $time > $j<submit> ?? $time - $j<submit> !! 0;
%result{$j<priority>} += $wait;
#printf "%s (prio %d): Submits at %3d, starts at %3d, ends at %3d. Wait time = %3d.\n",
# |$j<title priority submit>, $time, $ends, $wait;
$time = $ends;
}
do hyper for %result.keys.sort.reverse -> $prio {
"Priority-{$prio}: {%result{$prio} div $bag{$prio}}"
}
}
### Test
# format:
# JOB_ID,SUBMIT_TIMESTAMP,PROCESSING_TIME_MS,PRIORITY
my @data = (
q:to/EOI/,
jobA,0,10,3
jobB,2,5,1
jobC,3,8,3
jobD,7,4,2
EOI
q:to/EOI/,
jobB,2,5,1
jobA,0,10,3
jobC,3,8,3
jobD,7,4,2
jobE,20,4,3
EOI
q:to/EOI/,
jobA,0,5,1
jobB,100,10,5
jobC,101,5,5
EOI
);
for @data -> $data {
say schedule($data.chomp.split("\n"));
}