aboutsummaryrefslogtreecommitdiff
path: root/challenge-082/andinus
diff options
context:
space:
mode:
authorMohammad S Anwar <mohammad.anwar@yahoo.com>2020-10-12 06:28:15 +0100
committerMohammad S Anwar <mohammad.anwar@yahoo.com>2020-10-12 06:28:15 +0100
commit9fcf68b375fbdc5f308f72a00943c292db9e674f (patch)
tree069ee91dbbe2f72c1a54d7d0f2c46bd3a16a562e /challenge-082/andinus
parent47111c0321add0a2ec0ccd99bbb267bab17d1854 (diff)
downloadperlweeklychallenge-club-9fcf68b375fbdc5f308f72a00943c292db9e674f.tar.gz
perlweeklychallenge-club-9fcf68b375fbdc5f308f72a00943c292db9e674f.tar.bz2
perlweeklychallenge-club-9fcf68b375fbdc5f308f72a00943c292db9e674f.zip
- Added template for Challenge 82.
Diffstat (limited to 'challenge-082/andinus')
-rw-r--r--challenge-082/andinus/README162
1 files changed, 162 insertions, 0 deletions
diff --git a/challenge-082/andinus/README b/challenge-082/andinus/README
new file mode 100644
index 0000000000..13354ca364
--- /dev/null
+++ b/challenge-082/andinus/README
@@ -0,0 +1,162 @@
+ ━━━━━━━━━━━━━━━
+ CHALLENGE 081
+
+ Andinus
+ ━━━━━━━━━━━━━━━
+
+
+Table of Contents
+─────────────────
+
+1. Task 1 - Common Base String
+.. 1. Perl
+2. Task 2 - Frequency Sort
+.. 1. Perl
+
+
+
+
+
+1 Task 1 - Common Base String
+═════════════════════════════
+
+ You are given 2 strings, `$A' and `$B'.
+
+ Write a script to find out common base strings in `$A' and `$B'.
+
+ A substring of a string $S is called base string if
+ repeated concatenation of the substring results in the
+ string.
+
+
+1.1 Perl
+────────
+
+ • Program: <file:perl/ch-1.pl>
+
+ We will break `$A' & check if any subset of `$A' join to make `$B'. To
+ speed up the process we only break `$A' by common divisors of both
+ `$A' & `$B'.
+
+ I assume that the length of `$B' is greater than `$A' in later parts
+ so we make sure that it's true.
+ ┌────
+ │ my $A = shift @ARGV;
+ │ my $B = shift @ARGV;
+ │
+ │ # We assume length($B) is greater than length($A).
+ │ unless (length($B) > length($A)) {
+ │ my $tmp = $A;
+ │ $A = $B;
+ │ $B = $tmp;
+ │ }
+ └────
+
+ If the strings have different sets of characters then common base
+ string cannot exists so we exit early.
+ ┌────
+ │ # Check if common base string is even possible.
+ │ my (%chars_in_A, %chars_in_B);
+ │ $chars_in_A{$_} = 1 foreach split //, $A;
+ │ $chars_in_B{$_} = 1 foreach split //, $B;
+ │ foreach my $char (sort keys %chars_in_A) {
+ │ last if exists $chars_in_B{$char} ;
+ │ print "No common base string.\n" and exit 0
+ │ }
+ └────
+
+ Get all the common divisors of `$A' & `$B'.
+ ┌────
+ │ # Get all common divisors.
+ │ my %divisors_of_A = divisors(length($A));
+ │ my %divisors_of_B = divisors(length($B));
+ │ my @common_divisors;
+ │ foreach my $num (sort { $a <=> $b } keys %divisors_of_A) {
+ │ push @common_divisors, $num
+ │ if exists $divisors_of_B{$num};
+ │ }
+ │
+ │ # Returns all divisors of a number.
+ │ sub divisors {
+ │ my $n = shift @_;
+ │ my %divisors;
+ │ foreach my $i ( 1 ... $n){
+ │ if ($n % $i == 0) {
+ │ $divisors{$i} = 1;
+ │ }
+ │ }
+ │ return %divisors;
+ │ }
+ └────
+
+ We check if any subset of `$A' joins to make `$B'.
+ ┌────
+ │ my @common;
+ │
+ │ foreach my $num (@common_divisors){
+ │ my $tmp;
+ │ my $base = substr($A, 0, $num);
+ │ foreach (1 ... length($B) / $num) {
+ │ $tmp .= $base;
+ │ }
+ │ push @common, $base if $tmp eq $B;
+ │ }
+ │
+ │ print "No common base string.\n" and exit 0
+ │ unless scalar @common;
+ │ print join(', ', @common), "\n";
+ └────
+
+
+2 Task 2 - Frequency Sort
+═════════════════════════
+
+ You are given file named input.
+
+ Write a script to find the frequency of all the words.
+
+ It should print the result as first column of each line should be the
+ frequency of the the word followed by all the words of that frequency
+ arranged in lexicographical order. Also sort the words in the
+ ascending order of frequency.
+
+ For the sake of this task, please ignore the following in the input
+ file: `. " ( ) , 's --'
+
+
+2.1 Perl
+────────
+
+ • Program: <file:perl/ch-2.pl>
+
+ Swap unwanted characters with a space.
+ ┌────
+ │ my $file = path(shift @ARGV)->slurp;
+ │
+ │ $file =~ s/(--|'s)/ /g;
+ │ $file =~ s/[."(),]+/ /g;
+ │ $file =~ s/ / /g;
+ │ $file =~ s/\n/ /g;
+ └────
+
+ Get frequency of each word.
+ ┌────
+ │ my %words;
+ │ foreach my $word (split / /, $file) {
+ │ $words{$word} = 1 and next unless exists $words{$word};
+ │ $words{$word}++;
+ │ }
+ └────
+
+ Format the output.
+ ┌────
+ │ my %out;
+ │ foreach my $word (sort keys %words) {
+ │ my $freq = $words{$word};
+ │ push @{$out{$freq}}, $word;
+ │ }
+ │
+ │ foreach my $freq (sort { $a <=> $b} keys %out) {
+ │ print "$freq ", join(' ', @{$out{$freq}}, "\n");
+ │ }
+ └────