diff options
| author | Mohammad S Anwar <Mohammad.Anwar@yahoo.com> | 2020-01-25 16:40:24 +0000 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2020-01-25 16:40:24 +0000 |
| commit | 310394691a2d4665ffe84e9f491c8a53e74015ae (patch) | |
| tree | 97b22a7c7983cff9138f5228ca5d57099e9608f4 /challenge-044 | |
| parent | c926febeed866713d723c1d1aeeab62ccb0fce1f (diff) | |
| parent | 93f737924f3a70b21adea095e873d72282267e13 (diff) | |
| download | perlweeklychallenge-club-310394691a2d4665ffe84e9f491c8a53e74015ae.tar.gz perlweeklychallenge-club-310394691a2d4665ffe84e9f491c8a53e74015ae.tar.bz2 perlweeklychallenge-club-310394691a2d4665ffe84e9f491c8a53e74015ae.zip | |
Merge pull request #1166 from noudald/challenge-044-noud
Solutions to challenge 44 task 1 and 2 in Raku by Noud
Diffstat (limited to 'challenge-044')
| -rw-r--r-- | challenge-044/noud/raku/ch-1.p6 | 65 | ||||
| -rw-r--r-- | challenge-044/noud/raku/ch-2.p6 | 57 |
2 files changed, 122 insertions, 0 deletions
diff --git a/challenge-044/noud/raku/ch-1.p6 b/challenge-044/noud/raku/ch-1.p6 new file mode 100644 index 0000000000..6d24638566 --- /dev/null +++ b/challenge-044/noud/raku/ch-1.p6 @@ -0,0 +1,65 @@ +# Only 100, please. +# +# You are given a string “123456789”. Write a script that would insert ”+” or +# ”-” in between digits so that when you evaluate, the result should be 100. + + +# General calculator that handles + and - using Grammars. +grammar Calculator { + rule TOP { + <num>+ %% <op> + } + token op { '+' | '-' }; + token num { \d+ } +} + +class Arithm { + method TOP($/) { + my $res = $<num>[0]; + + loop (my $i = 1; $i < $<num>.elems; $i++) { + my $num = Int($<num>[$i]); + given $<op>[$i - 1] { + when '+' { $res += $num; } + when '-' { $res -= $num; } + } + } + + $/.make($res); + } +} + +# Subroutine helper that creates all combinations using + and - and uses +# Calculator grammar to check if the combination adds up to the target value. +sub _pmcomb($action, @rest, $target) { + if (@rest.elems == 0) { + my $result = Calculator.parse($action, :actions(Arithm)).made; + if ($result == $target) { + say $action ~ '=' ~ $result; + } + } elsif ($action.chars == 0) { + _pmcomb(Str(@rest.first), @rest.tail(*-1), $target); + } else { + _pmcomb($action ~ '+' ~ @rest.first, @rest.tail(*-1), $target); + _pmcomb($action ~ '-' ~ @rest.first, @rest.tail(*-1), $target); + _pmcomb($action ~ '' ~ @rest.first, @rest.tail(*-1), $target); + } +} + +sub pmcomb($str, $n) { + _pmcomb('', $str.comb, $n); +} + +sub pmcomb100($str) { + pmcomb($str, 100); +} + + +say "All arithmic combinations of 1234567890 that add up to 100:"; +pmcomb100('1234567890'); + +say "All arithmic combinations of 1234567890 that add up to 101:"; +pmcomb('1234567890', 101); + +say "All arithmic combinations of 1133557799 that add up to 42:"; +pmcomb('1133557799', 42); diff --git a/challenge-044/noud/raku/ch-2.p6 b/challenge-044/noud/raku/ch-2.p6 new file mode 100644 index 0000000000..808bf456d6 --- /dev/null +++ b/challenge-044/noud/raku/ch-2.p6 @@ -0,0 +1,57 @@ +# Make it $200 +# +# You have only $1 left at the start of the week. You have been given an +# opportunity to make it $200. The rule is simple with every move you can +# either double what you have or add another $1. Write a script to help you get +# $200 with the smallest number of moves. + +use experimental :cached; + +sub best-strategy($cur-val, $target=200) is cached { + if ($cur-val == $target) { + return 0, []; + } + if ($cur-val > $target) { + return -1, []; + } + + my ($d1, $strat1) = best-strategy(2 * $cur-val, $target); + my ($d2, $strat2) = best-strategy($cur-val + 1, $target); + + if ($d1 < 0 and $d2 < 0) { + return -1, []; + } + if ($d1 < 0) { + return $d2 + 1, (|($strat2), 2); + } + if ($d2 < 0) { + return $d1 + 1, (|($strat1), 1); + } + if ($d1 < $d2) { + return $d1 + 1, (|($strat1), 1); + } + else { + return $d2 + 1, (|($strat2), 2); + } +} + +sub print-strategy($target) { + my ($a, $b) = best-strategy(1, $target); + say "In $a moves we can get $target dollar:"; + my $r = ''; + for $b.list -> $s { + if ($s == 1) { + $r ~= "2*("; + } else { + $r ~= "1+("; + } + } + $r ~= '1' ~ (')' x $a); + say $r ~ "=$target"; +} + + +print-strategy(10); +print-strategy(200); +print-strategy(4200); +print-strategy(12345); |
