aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMyoungjin JEON <jeongoon@gmail.com>2020-10-07 23:38:04 +1100
committerMyoungjin JEON <jeongoon@gmail.com>2020-10-07 23:38:04 +1100
commit79ea68a3e085f2c7ce681ac2229f262e07430376 (patch)
treef47b3b3351e9e4a062012375959527e6576e1239
parent6d9c462f619cd7bd69ae1388cc584e184b19eafb (diff)
downloadperlweeklychallenge-club-79ea68a3e085f2c7ce681ac2229f262e07430376.tar.gz
perlweeklychallenge-club-79ea68a3e085f2c7ce681ac2229f262e07430376.tar.bz2
perlweeklychallenge-club-79ea68a3e085f2c7ce681ac2229f262e07430376.zip
[ch-081/jeongoon] Perl, Raku, Go solution added
-rw-r--r--challenge-081/jeongoon/go/ch-1.go62
-rw-r--r--challenge-081/jeongoon/go/ch-2.go103
l---------challenge-081/jeongoon/go/input1
-rw-r--r--challenge-081/jeongoon/perl/ch-1.pl45
-rw-r--r--challenge-081/jeongoon/perl/ch-2.pl41
-rw-r--r--challenge-081/jeongoon/perl/input3
-rw-r--r--challenge-081/jeongoon/raku/ch-1.raku39
-rw-r--r--challenge-081/jeongoon/raku/ch-2.raku52
l---------challenge-081/jeongoon/raku/input1
9 files changed, 347 insertions, 0 deletions
diff --git a/challenge-081/jeongoon/go/ch-1.go b/challenge-081/jeongoon/go/ch-1.go
new file mode 100644
index 0000000000..f1b43ef184
--- /dev/null
+++ b/challenge-081/jeongoon/go/ch-1.go
@@ -0,0 +1,62 @@
+/*
+Ref:
+https://golangbyexample.com/length-of-string-golang/
+https://golangdocs.com/concatenate-strings-in-golang
+*/
+
+// test with: go run ch-1.go abcabc abcabcabcabc
+
+
+package main
+
+import (
+ "os"
+ "fmt"
+ "strings"
+)
+
+func commonDivisors ( a int, b int ) []int {
+ var result []int
+ var min int
+ if a < b {
+ min = a
+ } else {
+ min = b }
+
+ for i := 1; i <= min; i++ {
+ if ( a % i == 0 && b % i ==0 ) {
+ result = append( result, i );
+ }
+ }
+ return result
+}
+
+// trying to make a method but it wasn't good idea :-/
+type StrTest string
+//https://stackoverflow.com/questions/28800672/how-to-add-new-methods-to-an-existing-type-in-go
+func (substr StrTest) RepeatedIn(str string) bool {
+ return (
+ len(str) % len(substr) == 0 &&
+ str == strings.Repeat( string(substr),
+ len(str) / len(substr) ) )
+}
+
+func main() {
+ AB := os.Args[1:3]
+
+ var baseStrings []string;
+
+ next_common_divisor:
+ for _, dv := range commonDivisors( len(AB[0]), len(AB[1]) ) {
+ mbs := AB[0][0:dv] // maybe base string
+ for _, x := range AB {
+ if ! StrTest(mbs).RepeatedIn( x ) {
+ continue next_common_divisor;
+ }
+ }
+ // copying is the only way??
+ baseStrings = append( baseStrings, mbs )
+ }
+
+ fmt.Println( strings.Join(baseStrings, " " ) )
+}
diff --git a/challenge-081/jeongoon/go/ch-2.go b/challenge-081/jeongoon/go/ch-2.go
new file mode 100644
index 0000000000..0f5af73735
--- /dev/null
+++ b/challenge-081/jeongoon/go/ch-2.go
@@ -0,0 +1,103 @@
+/*
+Ref:
+https://golangdocs.com/reading-files-in-golang
+https://golangdocs.com/split-string-in-golang
+https://golang.org/pkg/sort/
+*/
+
+/* test with: go run ./ch-1.go
+# reading from file named "input" in PWD
+*/
+
+package main
+import (
+ "fmt"
+ "io/ioutil"
+ "log"
+ "sort"
+ "strings"
+)
+
+func FilterStr(vs string, fs []string) string {
+ var vss []string
+ vslen := len(vs)
+
+ through_string:
+ for i := 0; i < vslen; {
+ for _, f := range fs {
+ flen := len(f)
+ if i+flen >= vslen {
+ break through_string
+ }
+ subv := vs[i:i+flen]
+ if subv == f {
+ i += flen
+ continue through_string
+ }
+ }
+ vss = append( vss, vs[i:i+1] )
+ i++
+ }
+ return strings.Join( vss, "" )
+}
+
+type WordBag map[string]int
+type FrequencyToWords map[int][]string
+
+func (wb *WordBag) FromSlice(ws []string) {
+ for _, w := range ws {
+ (*wb)[w]++
+ }
+}
+
+func (f2w *FrequencyToWords) Add(c int, w string) {
+ (*f2w)[c] = append( (*f2w)[c], w )
+}
+
+func (f2w *FrequencyToWords) Find(freq int) ([]string, bool) {
+ words, ok := (*f2w)[freq]
+ return words, ok
+}
+
+func (wb *WordBag) ExportFrequencyToWords() ([]int, *FrequencyToWords) {
+ frq_only := []int{}
+ f2w := make(FrequencyToWords)
+
+ for word, count := range (*wb) {
+ found := false
+ for _, cnt := range (frq_only) {
+ if count == cnt {
+ found = true
+ break
+ }
+ }
+ if ! found {
+ frq_only = append(frq_only, count)
+ }
+ f2w.Add(count, word)
+ }
+ sort.Ints(frq_only) // sorted in place
+ return frq_only, &f2w
+}
+
+func main() {
+ content, err := ioutil.ReadFile("input")
+ if err != nil {
+ log.Fatal(err)
+ }
+
+ words := strings.Fields(
+ FilterStr( string(content),
+ []string{ ".", ",", "(", ")", "\"", "'s", "--" },
+ ) )
+ bag := make(WordBag)
+ bag.FromSlice(words)
+ frq_sorted, freq_to_words := bag.ExportFrequencyToWords()
+ for _, frq := range(frq_sorted) {
+ ws, ok := freq_to_words.Find(frq)
+ if ok {
+ sort.Strings(ws)
+ fmt.Printf("%d\t%v\n", frq, strings.Join(ws, " "))
+ }
+ }
+}
diff --git a/challenge-081/jeongoon/go/input b/challenge-081/jeongoon/go/input
new file mode 120000
index 0000000000..8f1f9ce80d
--- /dev/null
+++ b/challenge-081/jeongoon/go/input
@@ -0,0 +1 @@
+../perl/input \ No newline at end of file
diff --git a/challenge-081/jeongoon/perl/ch-1.pl b/challenge-081/jeongoon/perl/ch-1.pl
new file mode 100644
index 0000000000..bf2b8cc99f
--- /dev/null
+++ b/challenge-081/jeongoon/perl/ch-1.pl
@@ -0,0 +1,45 @@
+#!/usr/bin/env perl
+# -*- Mode: cperl; cperl-indent-level:4 tab-width: 8; indent-tabs-mode: nil -*-
+# -*- coding: utf-8 -*-
+
+use strict; use warnings;
+use v5.26;
+use List::Util qw(all);
+
+sub usage {
+ say 'perl ch-1.pl [-v] <string> <string>', "\n",
+ 'ex) perl ch-1.pl "perlraku" "perlrakuperlrakuperlraku"';
+}
+
+sub unsafe_commonDivisors($$) {
+ my ( $l, $r ) = @_;
+ all { int($_) eq $_ } $l, $r or die "both should be numbers";
+
+ my $min = $l < $r ? $l : $r;
+ map { ( $l % $_ or $r % $_ ) ? () : $_ } 1 .. $min;
+}
+
+my @f_ARGV = grep { ! /-(v|d|-*verbsose|-*debug)/ } @ARGV;
+my ( $A, $B ) = @f_ARGV;
+
+our $d = @f_ARGV != @ARGV; # turn on verbose
+
+all { defined $_ and length $_ > 0 } $A, $B or usage, exit 0;
+
+my @commonBaseWords;
+
+for my $cdv ( unsafe_commonDivisors( length $A, length $B ) ) {
+ my $mcb = substr( $A, 0, $cdv ); # (m)aybe (c)ommon (b)ase string
+ ( all
+ { my @m = /$mcb/g;
+
+ say STDERR "`$_' contains `$mcb'", ": ",
+ (scalar @m), ", must be ", (length($_) / $cdv) if $d;
+
+ scalar( @m ) == (length($_) / $cdv)
+
+ } $A, $B
+ ) and push @commonBaseWords, $mcb;
+}
+
+say join(", ", @commonBaseWords);
diff --git a/challenge-081/jeongoon/perl/ch-2.pl b/challenge-081/jeongoon/perl/ch-2.pl
new file mode 100644
index 0000000000..3ba377515d
--- /dev/null
+++ b/challenge-081/jeongoon/perl/ch-2.pl
@@ -0,0 +1,41 @@
+#!/usr/bin/env perl
+# -*- Mode: cperl; cperl-indent-level:4 tab-width: 8; indent-tabs-mode: nil -*-
+# -*- coding: utf-8 -*-
+
+use strict; use warnings;
+use v5.26;
+use List::Util 1.39 qw(pairs);
+
+sub usage {
+ say 'perl ch-1.pl # no option: reading from a file named `input\'';
+}
+
+my @f_ARGV = grep { ! /-(h|-*help)/ } @ARGV;
+@f_ARGV == @ARGV or usage, exit 0;
+
+my ( $file_path, @words ) = "input";
+-r $file_path or usage, exit 0;
+
+open my $fh, '<', $file_path or die $@;
+
+{
+ local $/ = undef;
+ @words = split /\s/, <$fh>;
+};
+
+# filtering and add to bag
+my %prada;
+for my $w (@words) {
+ $w =~ s/'s|--|[^a-zA-Z_0-9\-]//g;
+ ++$prada{$w};
+}
+
+# invert frequency and word
+my %evilWares;
+for my $pair ( pairs %prada ) {
+ push @{$evilWares{$pair->value}}, $pair->key;
+}
+
+for my $freq ( sort ( keys %evilWares ) ) {
+ say "$freq @{[sort @{$evilWares{$freq}}]}";
+}
diff --git a/challenge-081/jeongoon/perl/input b/challenge-081/jeongoon/perl/input
new file mode 100644
index 0000000000..37001629ad
--- /dev/null
+++ b/challenge-081/jeongoon/perl/input
@@ -0,0 +1,3 @@
+West Side Story
+
+The award-winning adaptation of the classic romantic tragedy "Romeo and Juliet". The feuding families become two warring New York City gangs, the white Jets led by Riff and the Latino Sharks, led by Bernardo. Their hatred escalates to a point where neither can coexist with any form of understanding. But when Riff's best friend (and former Jet) Tony and Bernardo's younger sister Maria meet at a dance, no one can do anything to stop their love. Maria and Tony begin meeting in secret, planning to run away. Then the Sharks and Jets plan a rumble under the highway--whoever wins gains control of the streets. Maria sends Tony to stop it, hoping it can end the violence. It goes terribly wrong, and before the lovers know what's happened, tragedy strikes and doesn't stop until the climactic and heartbreaking ending.
diff --git a/challenge-081/jeongoon/raku/ch-1.raku b/challenge-081/jeongoon/raku/ch-1.raku
new file mode 100644
index 0000000000..005aee4818
--- /dev/null
+++ b/challenge-081/jeongoon/raku/ch-1.raku
@@ -0,0 +1,39 @@
+#!/usr/bin/env raku
+# -*- Mode: Raku; indent-tabs-mode: nil; coding: utf-8 -*-
+# vim: set et ts=4 sw=4:
+
+use v6.d;
+
+# tested with: raku jeongoon/raku/ch-1.raku perlraku perlrakuperlrakuperlraku
+
+=begin unfolded
+
+sub MAIN( *@a where @a.elems == 2 ) {
+ (1..[gcd] @a».chars).
+ map( ->\k {
+ my \w = @a[0].substr(^k); # a possible base (w)ord
+ # `-> it doesn't matter which words are in use
+ next if any @a.map({
+ .indices(w).elems
+ !=
+ .chars / k
+ } );
+ w # take
+ } ).join(", ").put
+}
+
+=end unfolded
+
+# https://dev.to/jeongoon/weekly-challenge-081-task-1-422l
+# folded
+sub MAIN(*@a){put (1..[gcd] @a».chars).map(->\k{my \w=@a[0].substr(^k);next if any @a.map({.indices(w)!= .chars/k});w})}
+
+=begin off-the-challenge
+
+# credit: markus-holzer
+# thank you :-)
+
+#sub MAIN(*@a){put ([\~] @a[0].substr(^ [gcd] @a».chars)).grep(->\w{all @a.map({.indices(w)==.chars/w.chars})})}
+sub MAIN(*@a){put ([\~] @a.min).grep(->\w{all @a.map({.indices(w)==.chars/w.chars})})}
+
+=end off-the-challenge
diff --git a/challenge-081/jeongoon/raku/ch-2.raku b/challenge-081/jeongoon/raku/ch-2.raku
new file mode 100644
index 0000000000..b77fff0b4e
--- /dev/null
+++ b/challenge-081/jeongoon/raku/ch-2.raku
@@ -0,0 +1,52 @@
+#!/usr/bin/env raku
+# -*- Mode: Raku; indent-tabs-mode: nil; coding: utf-8 -*-
+# vim: set et ts=4 sw=4:
+
+# test with:
+our $usage="cd jeongoon/raku; raku ch-2.raku; cd -";
+# because reading "input" from current directory
+
+=begin unfolded
+
+with "input".IO {
+ .r or die "no `input' file";
+ my %r;
+ %r{.value}.push(.key) .= sort # not efficent but note that
+ # left hand side is still left value
+ for bag(.words».
+ subst( / \'s
+ |
+ <[\W]-[-]> # non ascii num but `-' allowed
+ |
+ "--" /, # `-' is allowed but `--' is not
+ '',:g )
+ );
+ %r.sort(*.key). # `*.key' is not needed but has clearer meaning
+ join("\n").
+ put;
+}
+
+=end unfolded
+
+# https://dev.to/jeongoon/weekly-challenge-081-task-2-1lbj
+with "input".IO {
+ .r or die "no `input' file";
+ my %r;
+ %r{.value}.push(.key).=sort
+ for bag(.words».subst(/\'s|<[\W]-[-]>|"--"/,'',:g));
+ %r.sort.join("\n").put;
+}
+
+=begin off-the-challenge
+
+# credit: mark-anderson
+# thank you :-)
+
+"input".IO.slurp andthen {
+ my %r;
+ %r{.value}.push(.key).=sort
+ for bag(.subst(/\'s|<[,."()]>|"--"/,'',:g).words);
+ %r.sort.join("\n").put;
+}
+
+=end off-the-challenge
diff --git a/challenge-081/jeongoon/raku/input b/challenge-081/jeongoon/raku/input
new file mode 120000
index 0000000000..8f1f9ce80d
--- /dev/null
+++ b/challenge-081/jeongoon/raku/input
@@ -0,0 +1 @@
+../perl/input \ No newline at end of file