aboutsummaryrefslogtreecommitdiff
path: root/challenge-035
diff options
context:
space:
mode:
authorE. Choroba <choroba@matfyz.cz>2019-11-19 22:09:31 +0100
committerE. Choroba <choroba@matfyz.cz>2019-11-19 22:09:31 +0100
commit1f70f2b189133cea849162be2c8ed66ec3d32441 (patch)
tree47cf7512404d6b97d710a838d46f3f0ac86d3616 /challenge-035
parenta672e0d747ab37b4b54521c192e68b445b1c73ef (diff)
downloadperlweeklychallenge-club-1f70f2b189133cea849162be2c8ed66ec3d32441.tar.gz
perlweeklychallenge-club-1f70f2b189133cea849162be2c8ed66ec3d32441.tar.bz2
perlweeklychallenge-club-1f70f2b189133cea849162be2c8ed66ec3d32441.zip
Add solution to 035 (Binary Morse encode + decode) by E. Choroba
Diffstat (limited to 'challenge-035')
-rwxr-xr-xchallenge-035/e-choroba/perl5/pwc035.pl64
1 files changed, 64 insertions, 0 deletions
diff --git a/challenge-035/e-choroba/perl5/pwc035.pl b/challenge-035/e-choroba/perl5/pwc035.pl
new file mode 100755
index 0000000000..471813388e
--- /dev/null
+++ b/challenge-035/e-choroba/perl5/pwc035.pl
@@ -0,0 +1,64 @@
+#!/usr/bin/perl
+use warnings;
+use strict;
+
+my %to_morse = qw( a .- b -... c -.-. d -.. e . f ..-. g --. h ....
+ i .. j .--- k -.- l .-.. m -- n -. o --- p .--.
+ q --.- r .-. s ... t - u ..- v ...- w .-- x -..-
+ y -.-- z --.. );
+my %from_morse = ('/' => "", '//' => ' ', reverse %to_morse);
+
+my %to_binary = ('.' => 1,
+ '-' => 111,
+ "" => 0,
+ '/' => '000',
+ '//' => '0000000');
+my %from_binary = reverse %to_binary;
+
+sub encode_to_morse {
+ join('/', map $to_morse{$_} // "", split //, shift)
+}
+
+sub encode_to_binary_digits {
+ encode_to_morse(shift) =~ s,((?<=[-.])(?=[-.])|//?|[-.]),$to_binary{$1},gr
+}
+
+sub encode_to_binary {
+ pack 'b*', encode_to_binary_digits(shift)
+}
+
+sub decode_to_binary_digits {
+ unpack('b*', shift) =~ s/0*$//r
+}
+
+sub decode_to_morse {
+ join "",
+ map $from_binary{$_},
+ split /(0+)/,
+ decode_to_binary_digits(shift)
+}
+
+sub decode_from_binary {
+ join "", map $from_morse{$_}, split m{(/+)}, decode_to_morse(shift)
+}
+
+use Test::More tests => 6;
+
+my $input = 'just another';
+my $morse = '.---/..-/.../-//.-/-./---/-/...././.-.';
+my $digits = '101110111011100010101110001010100011100000001011100'
+ . '01110100011101110111000111000101010100010001011101';
+my $bin = join "", map chr,
+ 221, 29, 117, 84, 28, 208, 113, 113, 119, 28, 85, 68, 23;
+
+is encode_to_morse('just another'), $morse, 'encode to morse';
+
+is encode_to_binary_digits('just another'), $digits, 'encode to binary digits';
+
+is encode_to_binary('just another'), $bin, 'encode to binary';
+
+is decode_to_binary_digits($bin), $digits, 'decode to binary digits';
+
+is decode_to_morse($bin), $morse, 'decode to morse';
+
+is decode_from_binary($bin), $input, 'decode from binary';