5 use List::Util qw(any);
10 my ($srcs, $dstcount, $dst) = /(.*) => (\d+) (\w+)/;
11 my %srcs = reverse $srcs =~ /(\d+) (\w+)/g;
18 use List::Util qw(first);
25 while (my $w = first { $_ ne 'ORE' && $want{$_} } keys %want) {
27 my $rcount = int (($want{$w}+$r->{count}-1)/$r->{count});
28 # say "want $want{$w} of $w, rule has $r->{count}, need $rcount rules";
29 if ($rcount * $r->{count} > $want{$w}) {
30 $have{$w} = $rcount * $r->{count} - $want{$w};
33 for my $src (keys %{ $r->{srcs} }) {
34 my $need = $r->{srcs}->{$src} * $rcount;
36 if ($need >= $have{$src}) {
46 # say "want: ", join(', ', map { "$want{$_} of $_" } keys %want);
47 # say "have: ", join(', ', map { "$have{$_} of $_" } keys %have);
53 my $low = fuel_from_ore(1);
57 my $max_ore = 1_000_000_000_000;
58 $high *= 2 while fuel_from_ore($high) <= $max_ore;
62 $now = int(($high + $low) / 2);
63 if (fuel_from_ore($now) <= $max_ore) {
68 } while ($low + 1 < $high);