aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--challenge-152/dave-jacoby/blog1.txt1
-rw-r--r--challenge-152/dave-jacoby/blog2.txt1
-rw-r--r--challenge-152/dave-jacoby/perl/ch-1.pl69
-rw-r--r--challenge-152/dave-jacoby/perl/ch-2.pl167
4 files changed, 238 insertions, 0 deletions
diff --git a/challenge-152/dave-jacoby/blog1.txt b/challenge-152/dave-jacoby/blog1.txt
new file mode 100644
index 0000000000..5be5dd4d14
--- /dev/null
+++ b/challenge-152/dave-jacoby/blog1.txt
@@ -0,0 +1 @@
+https://jacoby.github.io/2022/02/15/functional-paths-weekly-challenge-152.html \ No newline at end of file
diff --git a/challenge-152/dave-jacoby/blog2.txt b/challenge-152/dave-jacoby/blog2.txt
new file mode 100644
index 0000000000..f8dd4f91e4
--- /dev/null
+++ b/challenge-152/dave-jacoby/blog2.txt
@@ -0,0 +1 @@
+https://jacoby.github.io/2022/02/16/think-inside-the-box-weekly-challenge-152-pt-2.html \ No newline at end of file
diff --git a/challenge-152/dave-jacoby/perl/ch-1.pl b/challenge-152/dave-jacoby/perl/ch-1.pl
new file mode 100644
index 0000000000..9ae0796fe6
--- /dev/null
+++ b/challenge-152/dave-jacoby/perl/ch-1.pl
@@ -0,0 +1,69 @@
+#!/usr/bin/env perl
+
+use strict;
+use warnings;
+use feature qw{ say postderef signatures state };
+no warnings qw{ experimental };
+
+use List::Util qw{ min sum };
+
+# This is inspired by a reading of the problem
+# from Adam Russell, who notes that there's no
+# direct down-left or down-right between 3 on
+# the second level and 2 on the third in this
+# triangle:
+#
+# 1
+# 5 3
+# 2 3 4
+# 7 1 0 2
+# 6 4 5 2 8
+#
+# A similar problem occurs with the 0 on the
+# fourth row of the second example:
+#
+# 5
+# 2 3
+# 4 1 5
+# 0 1 2 3
+# 7 2 4 1 9
+#
+# If the problem requires a solution that's less
+# using List::Util and more actual tree structures,
+# that solution will be forthcoming.
+
+my @examples;
+push @examples, '$triangle=[ [1], [5,3], [2,3,4], [7,1,0,2], [6,4,5,2,8] ]';
+push @examples, '$triangle=[ [5], [2,3], [4,1,5], [0,1,2,3], [7,2,4,1,9] ]';
+
+for my $e (@examples) {
+ my $triangle;
+ eval($e);
+
+ # let's do this the functional way?
+ my $path = join ' + ', map { min $_->@* } $triangle->@*;
+ my $sum = sum map { min $_->@* } $triangle->@*;
+
+ my $tree = make_tree($triangle);
+ say <<"END";
+ Input: $e
+ Output: $sum
+ Minimum Sum Path = $path => $sum
+$tree
+END
+}
+
+sub make_tree ( $src ) {
+ my $output = '';
+ my $n = 10;
+ my $i = 0;
+ while ( $src->[$i] ) {
+ my $line = join ' ', $src->[$i]->@*;
+ $output .= "\n";
+ $output .= ' ' x ( $n - $i );
+ $output .= $line;
+ $i++;
+ }
+
+ return $output;
+}
diff --git a/challenge-152/dave-jacoby/perl/ch-2.pl b/challenge-152/dave-jacoby/perl/ch-2.pl
new file mode 100644
index 0000000000..d980facf24
--- /dev/null
+++ b/challenge-152/dave-jacoby/perl/ch-2.pl
@@ -0,0 +1,167 @@
+#!/usr/bin/env perl
+
+use strict;
+use warnings;
+use feature qw{ say postderef signatures state };
+no warnings qw{ experimental };
+
+use List::Util qw{ min max sum };
+
+my @examples;
+push @examples, [ [ [ -1, 0 ], [ 2, 2 ] ], [ [ 0, -1 ], [ 4, 4 ] ] ];
+push @examples, [ [ [ -3, -1 ], [ 1, 3 ] ], [ [ -1, -3 ], [ 2, 2 ] ] ];
+push @examples, [ [ [ 0, 0 ], [ 1, 1 ] ], [ [ 2, 2 ], [ 3, 3 ] ] ];
+push @examples, [ [ [ 0, 0 ], [ 1, 1 ] ], [ [ 1, 1 ], [ 3, 3 ] ] ];
+push @examples, [ [ [ 0, 1 ], [ 5, 2 ] ], [ [ 2, 0 ], [ 4, 4 ] ] ];
+
+for my $e (@examples) {
+ my $area = find_area( $e->[0], $e->[1] );
+ say <<"END";
+ Input: Rectangle 1 => ($e->[0][0][0],$e->[0][0][1]), ($e->[0][1][0],$e->[0][1][1])
+ Rectangle 2 => ($e->[1][0][0],$e->[1][0][1]), ($e->[1][1][0],$e->[1][1][1])
+ Output: $area
+END
+}
+
+sub find_area ( @r ) {
+ my @ro = map { make_rectangle($_) } @r;
+ my $overlap = has_overlap(@ro);
+ my $area = 0;
+
+ if ($overlap) {
+ my $overlap = find_overlap(@r);
+ $area = sum map { area($_) } @ro;
+ $area -= area($overlap);
+ }
+ else {
+ $area = sum map { area($_) } @ro;
+ }
+ return $area;
+}
+
+sub area ( $r ) {
+ my $minx = min map { $_->[0] } $r->@*;
+ my $maxx = max map { $_->[0] } $r->@*;
+ my $miny = min map { $_->[1] } $r->@*;
+ my $maxy = max map { $_->[1] } $r->@*;
+ my $x = $maxx - $minx;
+ my $y = $maxy - $miny;
+ return $x * $y;
+}
+
+sub find_overlap ( $r1, $r2 ) {
+ my $maxx1 = max map { $_->[0] } $r1->@*;
+ my $maxx2 = max map { $_->[0] } $r2->@*;
+
+ my $maxy1 = max map { $_->[1] } $r1->@*;
+ my $maxy2 = max map { $_->[1] } $r2->@*;
+
+ my $minx1 = min map { $_->[0] } $r1->@*;
+ my $minx2 = min map { $_->[0] } $r2->@*;
+
+ my $miny1 = min map { $_->[1] } $r1->@*;
+ my $miny2 = min map { $_->[1] } $r2->@*;
+
+ my $minx = max( $minx1, $minx2 );
+ my $miny = max( $miny1, $miny2 );
+ my $maxx = min( $maxx1, $maxx2 );
+ my $maxy = min( $maxy1, $maxy2 );
+
+ return [ [ $minx, $miny ], [ $maxx, $maxy ] ];
+}
+
+sub has_overlap ( $r1, $r2 ) {
+ my $maxx1 = max map { $_->[0] } $r1->@*;
+ my $maxx2 = max map { $_->[0] } $r2->@*;
+
+ my $maxy1 = max map { $_->[1] } $r1->@*;
+ my $maxy2 = max map { $_->[1] } $r2->@*;
+
+ my $minx1 = min map { $_->[0] } $r1->@*;
+ my $minx2 = min map { $_->[0] } $r2->@*;
+
+ my $miny1 = min map { $_->[1] } $r1->@*;
+ my $miny2 = min map { $_->[1] } $r2->@*;
+
+ return max( $minx1, $minx2 ) < min( $maxx1, $maxx2 )
+ && max( $miny1, $miny2 ) < min( $maxy1, $maxy2 ) ? 1 : 0;
+}
+
+sub within ( $r1, $r2 ) {
+ my $within = 0;
+ my $minx = min map { $_->[0] } $r1->@*;
+ my $maxx = max map { $_->[0] } $r1->@*;
+ my $miny = min map { $_->[1] } $r1->@*;
+ my $maxy = max map { $_->[1] } $r1->@*;
+ for my $p ( $r2->@* ) {
+ my $x = $p->[0];
+ my $y = $p->[1];
+ if ( $x < $maxx
+ && $x > $minx
+ && $y < $maxy
+ && $y > $miny )
+ {
+ $within++;
+ }
+ }
+ return $within;
+}
+
+sub make_rectangle ( $r ) {
+ my @points;
+ my @x = map { $_->[0] } $r->@*;
+ my @y = map { $_->[1] } $r->@*;
+ for my $x (@x) {
+ for my $y (@y) {
+ push @points, [ $x, $y ];
+ }
+ }
+ return \@points;
+}
+
+sub draw_rectangles( @r ) {
+ my @x = map { $_->[0] } map { $_->@* } @r;
+ my @y = map { $_->[1] } map { $_->@* } @r;
+
+ my $minx = min(@x);
+ my $maxx = max(@x);
+ my $miny = min(@y);
+ my $maxy = max(@y);
+
+ my @xr = $minx - 1 .. $maxx + 1;
+ my @yr = reverse $miny - 1 .. $maxy + 1;
+
+ my @r2;
+ for my $r (@r) {
+ my $rec;
+ my @x = map { $_->[0] } $r->@*;
+ my @y = map { $_->[1] } $r->@*;
+ for my $x (@x) {
+ for my $y (@y) { push $rec->@*, [ $x, $y ]; }
+ push @r2, $rec;
+ }
+ }
+
+ my @graph;
+ for my $y (@yr) {
+ my $row = [];
+ for my $x (@xr) {
+ my $s = ' ';
+ $s = '.' if $x == 0;
+ $s = '.' if $y == 0;
+ $s = '+' if $x == 0 && $y == 0;
+ my $pp = 0;
+ for my $r (@r2) {
+ $pp++;
+ for my $p ( $r->@* ) {
+ if ( $p->[0] == $x ) {
+ if ( $p->[1] == $y ) { $s = $pp; }
+ }
+ }
+ }
+ push $row->@*, $s;
+ }
+ push @graph, $row;
+ }
+ say join "\n", '', ( map { join ' ', $_->@* } @graph ), '';
+}