aboutsummaryrefslogtreecommitdiff
path: root/challenge-079
diff options
context:
space:
mode:
authorShawn <shawnw.mobile@gmail.com>2020-09-26 22:05:56 -0700
committerShawn <shawnw.mobile@gmail.com>2020-09-26 22:06:46 -0700
commitc0d69878c9b41f89ee260b085cacd331780f13b4 (patch)
tree9aceb65c0b97aabe328076c0a886e2d31ffa2d72 /challenge-079
parent6970fae3e74395626428f4f89e426a2b312addb1 (diff)
downloadperlweeklychallenge-club-c0d69878c9b41f89ee260b085cacd331780f13b4.tar.gz
perlweeklychallenge-club-c0d69878c9b41f89ee260b085cacd331780f13b4.tar.bz2
perlweeklychallenge-club-c0d69878c9b41f89ee260b085cacd331780f13b4.zip
Challenge 079, both parts in perl
Diffstat (limited to 'challenge-079')
-rwxr-xr-xchallenge-079/shawn-wagner/perl/ch1.pl31
-rwxr-xr-xchallenge-079/shawn-wagner/perl/ch2.pl61
2 files changed, 92 insertions, 0 deletions
diff --git a/challenge-079/shawn-wagner/perl/ch1.pl b/challenge-079/shawn-wagner/perl/ch1.pl
new file mode 100755
index 0000000000..8071823e09
--- /dev/null
+++ b/challenge-079/shawn-wagner/perl/ch1.pl
@@ -0,0 +1,31 @@
+#!/usr/bin/env perl
+use warnings;
+use strict;
+use feature qw/say/;
+
+# Optionally use Bit::Fast version of popcount
+
+BEGIN {
+ eval {
+ require Bit::Fast;
+ Bit::Fast->import(qw/popcount/);
+ } or eval {
+ sub popcount {
+ # Quick and dirty alternative population count
+ my $binary = unpack "b*", pack("i", $_[0]);
+ return $binary =~ tr/1/1/;
+ }
+ }
+}
+
+sub task1 :prototype($) {
+ my $total = 0;
+ for my $n (1 .. $_[0]) {
+ my $bits = popcount $n;
+ $total += $bits;
+ }
+ say $total % 1000000007;
+}
+
+task1 4;
+task1 3;
diff --git a/challenge-079/shawn-wagner/perl/ch2.pl b/challenge-079/shawn-wagner/perl/ch2.pl
new file mode 100755
index 0000000000..2258192e05
--- /dev/null
+++ b/challenge-079/shawn-wagner/perl/ch2.pl
@@ -0,0 +1,61 @@
+#!/usr/bin/env perl
+use warnings;
+use strict;
+use feature qw/say/;
+use open qw/:std :locale/;
+use charnames qw/:full/;
+use List::Util qw/min max/;
+
+# Print histogram with fancy Unicode art.
+sub histogram {
+ my $highest = max @_;
+ for my $row (reverse 1 .. $highest) {
+ print "$row\N{BOX DRAWINGS LIGHT VERTICAL}";
+ for my $col (@_) {
+ printf "%s ", ($row <= $col ? "\N{FULL BLOCK}" : " ");
+ }
+ print "\n";
+ }
+ say " \N{BOX DRAWINGS LIGHT UP AND RIGHT}",
+ "\N{BOX DRAWINGS LIGHT HORIZONTAL}\N{BOX DRAWINGS LIGHT HORIZONTAL}" x @_;
+ say " @_";
+}
+
+sub find_next_wall :prototype(\@$) {
+ my ($N, $left) = @_;
+ my $i = $left + 1;
+ while ($N->[$i] < $N->[$left]) {
+ $i += 1;
+ if ($i >= @$N) {
+ die "Out of range: $left, $i";
+ }
+ }
+ return $i;
+}
+
+sub sum_area :prototype(\@$$) {
+ my ($N, $left, $right) = @_;
+ my $height = min @{$N}[$left, $right];
+ my $area = 0;
+ for (my $i = $left + 1; $i < $right; $i += 1) {
+ $area += $height - $N->[$i];
+ }
+ return $area;
+}
+
+sub task2 {
+ histogram @_;
+ my $width = @_;
+ my $area = 0;
+ for (my $i = 0; $i < $#_; ) {
+ my $left = $i;
+ my $right = find_next_wall @_, $left;
+ $area += sum_area @_, $left, $right;
+ $i = $right;
+ }
+ say $area;
+}
+
+task2 2, 1, 4, 1, 2, 5;
+print "\n";
+task2 3, 1, 3, 1, 1, 5;