Skip to content

Instantly share code, notes, and snippets.

@kevincolyer
Created January 26, 2020 19:36
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kevincolyer/9e2e5bdc5381c1edbd339e25d30e9ded to your computer and use it in GitHub Desktop.
Save kevincolyer/9e2e5bdc5381c1edbd339e25d30e9ded to your computer and use it in GitHub Desktop.
#!/usr/bin/perl6
use v6;
use Test;
=begin pod
Task 1
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.
=end pod
sub MAIN(Str $number="123456789", Int :$target=100, Bool :$verbose=False, Bool :$all=False){
# try base 8 digits of base 3
# 0=nothing
# 1=+
# 2=-
my Int $bal = 1;
my $solution="";
my $bits=($number.chars-1); # possible permutations
my $fail=True;
# EVAL was too slow so let's use an accumulator and operand to avoid it.
for 3..^(3**$bits) -> Int $i {
# accumulator
my Int $acc=0;
# initial
my $operand =$number.substr(0,1); # Prime with first digit
# operator is +1 for add or -1 for subtract
my Int $operator = 1; # we start off adding the operand to 0 so set to +1
my Int $j=$i;
my @sum = $number.comb;
# for visualisation of answer
my Str $solution="1";
# compose the sum
for 1..$bits -> $index {
my $k = $j % 3;
if $k== 0 {
$operand ~=@sum[$index];
$solution~=@sum[$index];
} elsif $k==1 {
$acc=$acc+($operand*$operator);
$operator = 1;
$operand=@sum[$index];
$solution~="+" ~ @sum[$index];
} elsif $k==2 {
$acc=$acc+($operand*$operator);
$operator = -1;
$operand=@sum[$index];
$solution~="-" ~ @sum[$index];
}
$j=$j div 3;
}
# flush remaining ops
$acc=$acc+($operand*$operator);
# Answer is in the accumulator
# visual answer is in $solution
say "$i) checking $solution = "~ $acc if $verbose && $i %% 100;
if $target == $acc {
say "$number -> $solution = {$target} (Checked $i of {3**$bits-3} potential solutions)";
$fail=False;
exit unless $all;
}
}
say "No solution found for $number targeting $target" if $fail;
}
#!/usr/bin/perl6
use v6;
use Test;
=begin pod
Task 2
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.
=end pod
# A simple example shows there are about 10 operations I can see. A best solution must be less than this.
# 200 100 50 25 24 12 6 3 1 1
# if I take 10 bits in base two, a 1 is add and a 0 is double.
# Count up to 2**10 and see if == 200, if better keep solution
constant TARGET = 200;
my Int $bal = 1;
my $bestSolution="";
my $bestSolutionMoves=TARGET; # about as infinite as we need
my $bits=TARGET/10; # just a guess
for ^2**10 -> Int $i {
my Int $j=$i;
my Int $sum = 1;
my Str $solution="1";
my int $moves=0;
for ^$bits {
if $j +& 0x1 == 1 {
$sum+=1;
last if $sum>TARGET;
$solution~="+1";
} else {
$sum*=2;
last if $sum>TARGET;
$solution~="x2";
}
$j=$j +> 1;
$moves++;
if $sum==TARGET {
last;
}
}
if $sum==TARGET and $moves < $bestSolutionMoves {
$bestSolution=$solution ~ "=" ~ TARGET;
$bestSolutionMoves=$moves;
}
}
say "$bestSolution in $bestSolutionMoves moves";
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment