diff options
| author | Mohammad S Anwar <Mohammad.Anwar@yahoo.com> | 2021-08-07 00:18:53 +0100 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-08-07 00:18:53 +0100 |
| commit | cc7a9cd80a316d5790af847522e9780ce2d01347 (patch) | |
| tree | d891ddbe60b534bc5c08a0161e0fdf7100828f18 | |
| parent | c5905e73263a05a786b53f038fda4016552caa8b (diff) | |
| parent | 874afffe9af88b02736f9543c1f926c3550297fb (diff) | |
| download | perlweeklychallenge-club-cc7a9cd80a316d5790af847522e9780ce2d01347.tar.gz perlweeklychallenge-club-cc7a9cd80a316d5790af847522e9780ce2d01347.tar.bz2 perlweeklychallenge-club-cc7a9cd80a316d5790af847522e9780ce2d01347.zip | |
Merge pull request #4669 from polettix/polettix/pwc124
Add polettix's solution to challenge-124
| -rw-r--r-- | challenge-124/polettix/blog.txt | 1 | ||||
| -rw-r--r-- | challenge-124/polettix/blog1.txt | 1 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/ch-1-start.pl | 1 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/ch-1.pl | 51 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/ch-2.pl | 76 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/cpanfile | 1 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/cpanfile.snapshot | 10 | ||||
| -rwxr-xr-x | challenge-124/polettix/perl/sightly.pl | 114 | ||||
| -rw-r--r-- | challenge-124/polettix/perl/virgo.eye | 49 | ||||
| -rw-r--r-- | challenge-124/polettix/raku/ch-1.raku | 3 | ||||
| -rw-r--r-- | challenge-124/polettix/raku/ch-2.raku | 22 |
11 files changed, 329 insertions, 0 deletions
diff --git a/challenge-124/polettix/blog.txt b/challenge-124/polettix/blog.txt new file mode 100644 index 0000000000..41e3f2f879 --- /dev/null +++ b/challenge-124/polettix/blog.txt @@ -0,0 +1 @@ +https://github.polettix.it/ETOOBUSY/2021/08/04/pwc124-happy-women-day/ diff --git a/challenge-124/polettix/blog1.txt b/challenge-124/polettix/blog1.txt new file mode 100644 index 0000000000..c4c8db844c --- /dev/null +++ b/challenge-124/polettix/blog1.txt @@ -0,0 +1 @@ +https://github.polettix.it/ETOOBUSY/2021/08/05/pwc124-tug-of-war/ diff --git a/challenge-124/polettix/perl/ch-1-start.pl b/challenge-124/polettix/perl/ch-1-start.pl new file mode 100644 index 0000000000..91043f4626 --- /dev/null +++ b/challenge-124/polettix/perl/ch-1-start.pl @@ -0,0 +1 @@ +open$f,'<',$0;$x=<$f>for 1,2;print s{\S}{#}gr while<$f>;print"\n" diff --git a/challenge-124/polettix/perl/ch-1.pl b/challenge-124/polettix/perl/ch-1.pl new file mode 100644 index 0000000000..2951e98acd --- /dev/null +++ b/challenge-124/polettix/perl/ch-1.pl @@ -0,0 +1,51 @@ +eval eval '"'. + + + ('`'|'/').('['^ + '+').('`'|'%').('`'| + '.').'\\'.'$'.('`'|'&'). + ','."'".'<'."'"."\,".'\\'. + '$'.('^'^('`'|'.'))."\;".'\\'. + '$'.('['^'#').'='.'<'.'\\'.'$'.( + '`'|'&').'>'.('`'|'&').('`'|'/').( + '['^')').('{'^ '[').('^'^('`' + |'/')).','. ('^'^(('`')| + ',')).';'.( '['^"\+").( +'['^"\)").( '`'|"\)").( +'`'|'.').( '['^'/').( +'{'^'[').( '['^"\("). +'\\'."\{". '\\'.'\\'. +('{'^'('). '\\'."\}". +'\\'."\{". "\#".'\\'. +'}'.("\`"| "'").('['^ +')').("\{"^ '[').('['^ +',').("\`"| '(').('`'| + ')').(('`')| ',').("\`"| + '%').'<'.''. '\\'."\$".( + '`'|'&').('>'). ';'.('['^'+').( + '['^')').('`'|')').('`'|'.').('['^ + '/').'\\'.'"'.'\\'.'\\'.('`'|'.' + ).'\\'.'"'.('!'^'+').'"';$:= + '.'^'~';$~='@'|'(';$^=')'^ + '[';$/='`'|'.';$,='('^ + '}';$\='`'|"\!"; + $:=')'^'}' + ;$~=('*')| + '`';$^='+' + ^('_');$/= + '&'|'@';$, + ='['&"\~"; + $\=','^'|' + ;$:=('.')^ + '~';$~='@'|'(';$^=')'^"\[";$/= + '`'|'.';$,='('^'}';$\='`'|'!'; + $:=')'^'}';$~='*'|'`';$^="\+"^ + '_';$/='&'|'@';$,='['&"\~";$\= + ','^'|';$:='.'^'~';$~='@'|'('; + $^=')'^'[';$/='`'|'.';$,="\("^ + '}';$\='`' + |('!');$:= + ')'^'}';$~ + ='*'|"\`"; + $^='+'^'_' + ;$/=('&'); diff --git a/challenge-124/polettix/perl/ch-2.pl b/challenge-124/polettix/perl/ch-2.pl new file mode 100644 index 0000000000..277c6090a8 --- /dev/null +++ b/challenge-124/polettix/perl/ch-2.pl @@ -0,0 +1,76 @@ +#!/usr/bin/env perl +use v5.24; +use warnings; +use experimental 'signatures'; +no warnings 'experimental::signatures'; +use List::Util 'sum'; + +use constant TOLERANCE => 1E-7; + +my @input = @ARGV ? @ARGV : qw< 10 20 30 40 50 60 70 80 90 100 >; +my @subsets = tug_of_war(@input); +say 'Subset ', $_ + 1, ': (', join(', ', $subsets[$_]->@*), ')' for 0 .. 1; + +sub tug_of_war (@set) { + my $n = scalar @set; # number of elements in the set + my $n_2 = $n % 2 ? ($n - 1) / 2 : $n / 2; # size of "smaller" subset + my $subset_target = sum(@set) / 2; # target "half" of sum + + # we will go through the possible combinations of $n_2 elements out + # of our $n in the @set, checking their sum against the "subset target" + # of one-half of the total sum + my $cit = combinations_iterator($n_2, @set); + + # this will keep our "best" rolling solution during the iteration, and + # the absolute best at the end + my ($solution, $solution_delta); + while (my @subsets = $cit->()) { + # our combinations_iterator returns both the $n_2 subset, as well as + # the remaining items. We will concentrate the sum on the first + # sub-array, i.e. the first subset + + # we evaluate how far we are from the target sum for a subset. We + # don't care about the sign, just "how much" we're far off + my $subset_delta = abs(sum($subsets[0]->@*) - $subset_target); + + # update our current best according to the new combination. This also + # takes care of the initialization at the first pass, thanks to the + # check for !$solution + ($solution, $solution_delta) = (\@subsets, $subset_delta) + if (!$solution) || ($solution_delta > $subset_delta); + + # if we're below the tolerance for our distance to the target, let's + # call it a day and return this solution! + last if $subset_delta < TOLERANCE; + } + return $solution->@*; +} + +sub combinations_iterator ($k, @items) { + my @indexes = (0 .. ($k - 1)); + my $n = @items; + return sub { + return unless @indexes; + my (@combination, @remaining); + my $j = 0; + for my $i (0 .. ($n - 1)) { + if ($j < $k && $i == $indexes[$j]) { + push @combination, $items[$i]; + ++$j; + } + else { + push @remaining, $items[$i]; + } + } + for my $incc (reverse(-1, 0 .. ($k - 1))) { + if ($incc < 0) { + @indexes = (); # finished! + } + elsif ((my $v = $indexes[$incc]) < $incc - $k + $n) { + $indexes[$_] = ++$v for $incc .. ($k - 1); + last; + } + } + return (\@combination, \@remaining); + } +} diff --git a/challenge-124/polettix/perl/cpanfile b/challenge-124/polettix/perl/cpanfile new file mode 100644 index 0000000000..50fdc9d31e --- /dev/null +++ b/challenge-124/polettix/perl/cpanfile @@ -0,0 +1 @@ +requires 'Acme::EyeDrops'; diff --git a/challenge-124/polettix/perl/cpanfile.snapshot b/challenge-124/polettix/perl/cpanfile.snapshot new file mode 100644 index 0000000000..24634a16bf --- /dev/null +++ b/challenge-124/polettix/perl/cpanfile.snapshot @@ -0,0 +1,10 @@ +# carton snapshot format: version 1.0 +DISTRIBUTIONS + Acme-EyeDrops-1.62 + pathname: A/AS/ASAVIGE/Acme-EyeDrops-1.62.tar.gz + provides: + Acme::EyeDrops 1.62 + requirements: + Exporter 0 + ExtUtils::MakeMaker 0 + perl 5.006 diff --git a/challenge-124/polettix/perl/sightly.pl b/challenge-124/polettix/perl/sightly.pl new file mode 100755 index 0000000000..80248f2d62 --- /dev/null +++ b/challenge-124/polettix/perl/sightly.pl @@ -0,0 +1,114 @@ +#!/usr/bin/perl +# sightly.pl. + +use strict; +use Getopt::Std (); + +use FindBin '$Bin'; +use lib "$Bin/local/lib/perl5"; +use Acme::EyeDrops qw(sightly); + +sub usage +{ + print STDERR <<'EOM'; +usage: sightly [-s shape] [-f file|-z string] +Options: + -s shape Shape/s. Can specify multiple shapes separated + by commas. + A shape is just a file with a .eye suffix, + so you can add new shapes yourself. + -f file The file to be made sightly. + -z string Specify a string instead of a file. + -c string String used with -s banner above. + -p Print instead of eval. + -r [123] Regex attribute. Insert sightly into a regex. + -m Use compact sightly encoding. + -t Pour unsightly text. + -u textfiller Filler for -t option. + -U filler FillerVar. + -g gap Gap between successive shapes. + -o degree Rotate shape 90, 180, 270 degrees. + -a rtype Rotate type (0, 1 or 2). + -k Rotate flip. + -x bordergap Border gap. + -y borderwidth Border width. + -i Invert shape. + -R Remove newlines from source text. + -T Add trailing spaces to output shape. + -n gap Indent shape gap spaces. + -e Reflect shape. + -d fact Reduce shape by a factor of fact. + -v fact Expand shape by a factor of fact. + -b Binary file. + -w width Width. + -l List available shapes. + -E Trap die within eval with 'die $@ if $@' + -W Trap warnings with '$SIG{__WARN__}=sub{}' +Examples: + sightly -s camel -f myprog.pl >myprog2.pl + This creates myprog2.pl, equivalent to the original + myprog.pl, but prettier and shaped like a camel. + sightly -p -r 1 -s window -z "Bill Gates is a pest!\n" >bill.pl + This creates bill.pl, a program that prints the above string. + sightly -g 3 -bps camel,mongers -f some_binary_file >eyesore + This creates eyesore, a sightly-encoded file. + To decode it: perl eyesore > f.tmp + To check it worked: cmp f.tmp some_binary_file +Notes: + If no shape is specified, a single (very long) line will be output. + If a shape, but no file, is specified, a default no-op filler will + be used to fill the shape. +EOM + exit 1; +} + +sub list_shapes { + my @builtin = Acme::EyeDrops::get_builtin_shapes(); + my @eye = Acme::EyeDrops::get_eye_shapes(); + print "builtin shapes : @builtin\n"; + print ".eye file shapes: @eye\n"; +} + +my %optarg = ( + a => 'RotateType', + b => 'Binary', + c => 'BannerString', + d => 'Reduce', + e => 'Reflect', + f => 'SourceFile', + g => 'Gap', + i => 'Invert', + k => 'RotateFlip', + m => 'Compact', + n => 'Indent', + o => 'Rotate', + p => 'Print', + r => 'Regex', + s => 'Shape', + t => 'Text', + u => 'TextFiller', + U => 'FillerVar', + v => 'Expand', + w => 'Width', + x => 'BorderGap', + y => 'BorderWidth', + z => 'SourceString', + E => 'TrapEvalDie', + R => 'RemoveNewlines', + T => 'TrailingSpaces', + W => 'TrapWarn', +); + +usage() unless @ARGV; +my %arg = (); my %option = (); +Getopt::Std::getopts("hbeiklmptERTWa:c:d:f:g:n:o:r:s:u:U:v:w:x:y:z:", \%option) + or usage(); +usage() if $option{h}; +$option{l} and list_shapes(),exit(0); +$option{z} =~ s#\\n#\n#g if $option{z}; +for my $k (keys %option) { + next unless exists($option{$k}); + exists($optarg{$k}) and $arg{$optarg{$k}} = $option{$k}; +} +usage() if @ARGV; +print sightly(\%arg); diff --git a/challenge-124/polettix/perl/virgo.eye b/challenge-124/polettix/perl/virgo.eye new file mode 100644 index 0000000000..6016d31d4d --- /dev/null +++ b/challenge-124/polettix/perl/virgo.eye @@ -0,0 +1,49 @@ + ############### + #################### + ######################## + ########################## + ############################## + ################################ + ################################## + ############## ############## + ########### ############ + ########### ########### +########### ########### +########## ########## +########## ########## +########## ########## +########## ########## +########## ########## +########## ########## +########### ########## +########### ########## + ############ ########### + ############ ########### + ############### ############### + ################################## + ################################ + ############################ + ########################## + ###################### + ################ + ########## + ########## + ########## + ########## + ########## + ########## + ########## + ########## + ############################## + ############################## + ############################## + ############################## + ############################## + ############################## + ########## + ########## + ########## + ########## + ########## + ########## + diff --git a/challenge-124/polettix/raku/ch-1.raku b/challenge-124/polettix/raku/ch-1.raku new file mode 100644 index 0000000000..40f58b9d0f --- /dev/null +++ b/challenge-124/polettix/raku/ch-1.raku @@ -0,0 +1,3 @@ +#!/usr/bin/env raku +use v6; +put "♀" diff --git a/challenge-124/polettix/raku/ch-2.raku b/challenge-124/polettix/raku/ch-2.raku new file mode 100644 index 0000000000..73444fd4fe --- /dev/null +++ b/challenge-124/polettix/raku/ch-2.raku @@ -0,0 +1,22 @@ +#!/usr/bin/env raku +use v6; + +constant \TOLERANCE = 1E-7; + +my @input = @*ARGS ?? @*ARGS !! (1..10).map: * * 10; +my @subsets = tug-of-war(@input); +put 'Subset ', $_ + 1, ': (', @subsets[$_].join(', '), ')' for 0 .. 1; + +sub tug-of-war (@set) { + my $n = @set.elems; # number of elements in the set + my $n_2 = $n %% 2 ?? $n / 2 !! ($n - 1) / 2; # size of "smaller" subset + my $subset_target = @set.sum / 2; # target "half" of sum + my (@solution, $solution_delta); + for @set.combinations($n_2) -> @subset { + my $subset_delta = abs(@subset.sum - $subset_target); + ($solution_delta, @solution) = ($subset_delta, |@subset) + if (!defined($solution_delta)) || ($solution_delta > $subset_delta); + last if $solution_delta < TOLERANCE; + } + return (@solution, (@set (-) @solution).keys); +} |
