aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMohammad Sajid Anwar <Mohammad.Anwar@yahoo.com>2025-09-06 09:56:44 +0100
committerGitHub <noreply@github.com>2025-09-06 09:56:44 +0100
commitc3b746301adc1d6c8b64386ac75d353c28e0ad62 (patch)
tree072d76460f073391a5083037ce3559ee3c06be01
parent2a566dd79aad10642ac37c3b92dd976985f77823 (diff)
parent8689926595e9c553f50214926fa695b695982123 (diff)
downloadperlweeklychallenge-club-c3b746301adc1d6c8b64386ac75d353c28e0ad62.tar.gz
perlweeklychallenge-club-c3b746301adc1d6c8b64386ac75d353c28e0ad62.tar.bz2
perlweeklychallenge-club-c3b746301adc1d6c8b64386ac75d353c28e0ad62.zip
Merge pull request #12630 from PerlMonk-Athanasius/branch-for-challenge-337
Perl & Raku solutions to Tasks 1 & 2 for Week 337
-rw-r--r--challenge-337/athanasius/perl/ch-1.pl194
-rw-r--r--challenge-337/athanasius/perl/ch-2.pl417
-rw-r--r--challenge-337/athanasius/raku/ch-1.raku187
-rw-r--r--challenge-337/athanasius/raku/ch-2.raku405
4 files changed, 1203 insertions, 0 deletions
diff --git a/challenge-337/athanasius/perl/ch-1.pl b/challenge-337/athanasius/perl/ch-1.pl
new file mode 100644
index 0000000000..c5c8776b87
--- /dev/null
+++ b/challenge-337/athanasius/perl/ch-1.pl
@@ -0,0 +1,194 @@
+#!perl
+
+################################################################################
+=comment
+
+Perl Weekly Challenge 337
+=========================
+
+TASK #1
+-------
+*Smaller Than Current*
+
+Submitted by: Mohammad Sajid Anwar
+
+You are given an array of numbers, @num1.
+
+Write a script to return an array, @num2, where $num2[i] is the count of all
+numbers less than or equal to $num1[i].
+
+Example 1
+
+ Input: @num1 = (6, 5, 4, 8)
+ Output: (2, 1, 0, 3)
+
+ index 0: numbers <= 6 are 5, 4 => 2
+ index 1: numbers <= 5 are 4 => 1
+ index 2: numbers <= 4, none => 0
+ index 3: numbers <= 8 are 6, 5, 4 => 3
+
+Example 2
+
+ Input: @num1 = (7, 7, 7, 7)
+ Output: (3, 3, 3, 3)
+
+Example 3
+
+ Input: @num1 = (5, 4, 3, 2, 1)
+ Output: (4, 3, 2, 1, 0)
+
+Example 4
+
+ Input: @num1 = (-1, 0, 3, -2, 1)
+ Output: (1, 2, 4, 0, 3)
+
+Example 5
+
+ Input: @num1 = (0, 1, 1, 2, 0)
+ Output: (1, 3, 3, 4, 1)
+
+=cut
+################################################################################
+
+#--------------------------------------#
+# Copyright © 2025 PerlMonk Athanasius #
+#--------------------------------------#
+
+#===============================================================================
+=comment
+
+Assumptions
+-----------
+1. The input numbers are integers.
+2. The Task should read:
+
+ Write a script to return an array, @num2, where $num2[i] is the count of
+ all *other* numbers less than or equal to $num1[i].
+
+Interface
+---------
+1. If no command-line arguments are given, the test suite is run. Otherwise:
+2. A non-empty list of integers is entered on the command-line.
+
+=cut
+#===============================================================================
+
+use v5.38.2; # Enables strictures
+use warnings;
+use Const::Fast;
+use Regexp::Common qw( number );
+use Test::More;
+
+const my $USAGE => <<END;
+Usage:
+ perl $0 [<num1> ...]
+ perl $0
+
+ [<num1> ...] A non-empty list of integers
+END
+#-------------------------------------------------------------------------------
+BEGIN
+#-------------------------------------------------------------------------------
+{
+ $| = 1;
+ print "\nChallenge 337, Task #1: Smaller Than Current (Perl)\n\n";
+}
+
+#===============================================================================
+MAIN:
+#===============================================================================
+{
+ if (scalar @ARGV == 0)
+ {
+ run_tests();
+ }
+ else
+ {
+ my @num1 = @ARGV;
+
+ for (@num1)
+ {
+ / ^ $RE{num}{int} $ /x or error( qq["$_" is not a valid integer] );
+ }
+
+ printf "Input: \@num1 = (%s)\n", join ', ', @num1;
+
+ my $num2 = smaller_than_current( \@num1 );
+
+ printf "Output: (%s)\n", join ', ', @$num2;
+ }
+}
+
+#-------------------------------------------------------------------------------
+sub smaller_than_current
+#-------------------------------------------------------------------------------
+{
+ my ($num1) = @_;
+ my %freq;
+ ++$freq{$_} for @$num1;
+
+ my @keys = sort { $a <=> $b } keys %freq;
+ my $sum = 0;
+ my %cum_freq;
+
+ for my $key (@keys)
+ {
+ $sum += $freq{$key};
+ $cum_freq{$key} = $sum;
+ }
+
+ my @num2;
+
+ for my $num (@$num1)
+ {
+ push @num2, $cum_freq{$num} - 1;
+ }
+
+ return \@num2;
+}
+
+#-------------------------------------------------------------------------------
+sub run_tests
+#-------------------------------------------------------------------------------
+{
+ print "Running the test suite\n";
+
+ while (my $line = <DATA>)
+ {
+ chomp $line;
+
+ my ($test_name, $num1_str, $expd_str) = split / \| /x, $line;
+
+ for ($test_name, $num1_str, $expd_str)
+ {
+ s/ ^ \s+ //x;
+ s/ \s+ $ //x;
+ }
+
+ my @num1 = split / \s+ /x, $num1_str;
+ my $num2 = smaller_than_current( \@num1 );
+ my @expd = split / \s+ /x, $expd_str;
+
+ is_deeply $num2, \@expd, $test_name;
+ }
+
+ done_testing;
+}
+
+#-------------------------------------------------------------------------------
+sub error
+#-------------------------------------------------------------------------------
+{
+ my ($message) = @_;
+
+ die "ERROR: $message\n$USAGE";
+}
+
+################################################################################
+
+__DATA__
+Example 1| 6 5 4 8 |2 1 0 3
+Example 2| 7 7 7 7 |3 3 3 3
+Example 3| 5 4 3 2 1|4 3 2 1 0
+Example 4|-1 0 3 -2 1|1 2 4 0 3
+Example 5| 0 1 1 2 0|1 3 3 4 1
diff --git a/challenge-337/athanasius/perl/ch-2.pl b/challenge-337/athanasius/perl/ch-2.pl
new file mode 100644
index 0000000000..e9345cf2e0
--- /dev/null
+++ b/challenge-337/athanasius/perl/ch-2.pl
@@ -0,0 +1,417 @@
+#!perl
+
+################################################################################
+=comment
+
+Perl Weekly Challenge 337
+=========================
+
+TASK #2
+-------
+*Odd Matrix*
+
+Submitted by: Mohammad Sajid Anwar
+
+You are given row and col, also a list of positions in the matrix.
+
+Write a script to perform action on each location (0-indexed) as provided in the
+list and find out the total odd valued cells.
+
+For each location (r, c), do both of the following:
+
+ a) Increment by 1 all the cells on row r.
+ b) Increment by 1 all the cells on column c.
+
+Example 1
+
+ Input: $row = 2, $col = 3, @locations = ([0,1],[1,1])
+ Output: 6
+
+ Initial:
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+
+ Apply [0,1]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 ] [ 1 1 1 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ Increment col 1:
+ Before After
+ [ 1 1 1 ] [ 1 2 1 ]
+ [ 0 0 0 ] [ 0 1 0 ]
+
+ Apply [1,1]:
+ Increment row 1:
+ Before After
+ [ 1 2 1 ] [ 1 2 1 ]
+ [ 0 1 0 ] [ 1 2 1 ]
+ Increment col 1:
+ Before After
+ [ 1 2 1 ] [ 1 3 1 ]
+ [ 1 2 1 ] [ 1 3 1 ]
+
+ Final:
+ [ 1 3 1 ]
+ [ 1 3 1 ]
+
+Example 2
+
+ Input: $row = 2, $col = 2, @locations = ([1,1],[0,0])
+ Output: 0
+
+ Initial:
+ [ 0 0 ]
+ [ 0 0 ]
+
+ Apply [1,1]:
+ Increment row 1:
+ Before After
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 1 1 ]
+ Increment col 1:
+ Before After
+ [ 0 0 ] [ 0 1 ]
+ [ 1 1 ] [ 1 2 ]
+
+ Apply [0,0]:
+ Increment row 0:
+ Before After
+ [ 0 1 ] [ 1 2 ]
+ [ 1 2 ] [ 1 2 ]
+ Increment col 0:
+ Before After
+ [ 1 2 ] [ 2 2 ]
+ [ 1 2 ] [ 2 2 ]
+
+ Final:
+ [ 2 2 ]
+ [ 2 2 ]
+
+Example 3
+
+ Input: $row = 3, $col = 3, @locations = ([0,0],[1,2],[2,1])
+ Output: 0
+
+ Initial:
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+
+ Apply [0,0]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 ] [ 1 1 1 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ Increment col 0:
+ Before After
+ [ 1 1 1 ] [ 2 1 1 ]
+ [ 0 0 0 ] [ 1 0 0 ]
+ [ 0 0 0 ] [ 1 0 0 ]
+
+ Apply [1,2]:
+ Increment row 1:
+ Before After
+ [ 2 1 1 ] [ 2 1 1 ]
+ [ 1 0 0 ] [ 2 1 1 ]
+ [ 1 0 0 ] [ 1 0 0 ]
+ Increment col 2:
+ Before After
+ [ 2 1 1 ] [ 2 1 2 ]
+ [ 2 1 1 ] [ 2 1 2 ]
+ [ 1 0 0 ] [ 1 0 1 ]
+
+ Apply [2,1]:
+ Increment row 2:
+ Before After
+ [ 2 1 2 ] [ 2 1 2 ]
+ [ 2 1 2 ] [ 2 1 2 ]
+ [ 1 0 1 ] [ 2 1 2 ]
+ Increment col 1:
+ Before After
+ [ 2 1 2 ] [ 2 2 2 ]
+ [ 2 1 2 ] [ 2 2 2 ]
+ [ 2 1 2 ] [ 2 2 2 ]
+
+ Final:
+ [ 2 2 2 ]
+ [ 2 2 2 ]
+ [ 2 2 2 ]
+
+Example 4
+
+ Input: $row = 1, $col = 5, @locations = ([0,2],[0,4])
+ Output: 2
+
+ Initial:
+ [ 0 0 0 0 0 ]
+
+ Apply [0,2]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 0 0 ] [ 1 1 1 1 1 ]
+ Increment col 2:
+ Before After
+ [ 1 1 1 1 1 ] [ 1 1 2 1 1 ]
+
+ Apply [0,4]:
+ Increment row 0:
+ Before After
+ [ 1 1 2 1 1 ] [ 2 2 3 2 2 ]
+ Increment col 4:
+ Before After
+ [ 2 2 3 2 2 ] [ 2 2 3 2 3 ]
+
+ Final:
+ [ 2 2 3 2 3 ]
+
+Example 5
+
+ Input: $row = 4, $col = 2, @locations = ([1,0],[3,1],[2,0],[0,1])
+ Output: 8
+
+Initial:
+ [ 0 0 ]
+ [ 0 0 ]
+ [ 0 0 ]
+ [ 0 0 ]
+
+ Apply [1,0]:
+ Increment row 1:
+ Before After
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 1 1 ]
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 0 0 ]
+ Increment col 0:
+ Before After
+ [ 0 0 ] [ 1 0 ]
+ [ 1 1 ] [ 2 1 ]
+ [ 0 0 ] [ 1 0 ]
+ [ 0 0 ] [ 1 0 ]
+
+ Apply [3,1]:
+ Increment row 3:
+ Before After
+ [ 1 0 ] [ 1 0 ]
+ [ 2 1 ] [ 2 1 ]
+ [ 1 0 ] [ 1 0 ]
+ [ 1 0 ] [ 2 1 ]
+ Increment col 1:
+ Before After
+ [ 1 0 ] [ 1 1 ]
+ [ 2 1 ] [ 2 2 ]
+ [ 1 0 ] [ 1 1 ]
+ [ 2 1 ] [ 2 2 ]
+
+ Apply [2,0]:
+ Increment row 2:
+ Before After
+ [ 1 1 ] [ 1 1 ]
+ [ 2 2 ] [ 2 2 ]
+ [ 1 1 ] [ 2 2 ]
+ [ 2 2 ] [ 2 2 ]
+ Increment col 0:
+ Before After
+ [ 1 1 ] [ 2 1 ]
+ [ 2 2 ] [ 3 2 ]
+ [ 2 2 ] [ 3 2 ]
+ [ 2 2 ] [ 3 2 ]
+
+ Apply [0,1]:
+ Increment row 0:
+ Before After
+ [ 2 1 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ Increment col 1:
+ Before After
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+
+ Final:
+ [ 3 3 ]
+ [ 3 3 ]
+ [ 3 3 ]
+ [ 3 3 ]
+
+=cut
+################################################################################
+
+#--------------------------------------#
+# Copyright © 2025 PerlMonk Athanasius #
+#--------------------------------------#
+
+#===============================================================================
+=comment
+
+Interface
+---------
+1. If no command-line arguments are given, the test suite is run. Otherwise:
+2. Matrix dimensions (rows and columns) are entered on the command-line, follow-
+ ed by a list of coordinates describing positions within the matrix. The co-
+ ordinates are 0-indexed (row, column) integer pairs.
+
+=cut
+#===============================================================================
+
+use v5.38.2; # Enables strictures
+use warnings;
+use Const::Fast;
+use List::MoreUtils qw( natatime );
+use Regexp::Common qw( number );
+use Test::More;
+
+const my $USAGE => <<END;
+Usage:
+ perl $0 <row> <col> [<coords> ...]
+ perl $0
+
+ <row> Number of matrix rows
+ <col> Number of matrix columns
+ [<coords> ...] A list of matrix coordinate pairs
+END
+
+#-------------------------------------------------------------------------------
+BEGIN
+#-------------------------------------------------------------------------------
+{
+ $| = 1;
+ print "\nChallenge 337, Task #2: Odd Matrix (Perl)\n\n";
+}
+
+#===============================================================================
+MAIN:
+#===============================================================================
+{
+ my $argc = scalar @ARGV;
+
+ if ($argc == 0)
+ {
+ run_tests();
+ }
+ elsif ($argc == 1)
+ {
+ error( 'Expected 0 or 2+ command-line arguments, found 1' );
+ }
+ else
+ {
+ my ($row, $col, $positions) = parse_input( @ARGV );
+
+ printf "Input: \$row = $row, \$col = $col, \@locations = (%s)\n",
+ join ',', map { '[' . join( ',', @$_ ) . ']' } @$positions;
+
+ my $odd = odd_cells( $row, $col, $positions );
+
+ print "Output: $odd\n";
+ }
+}
+
+#-------------------------------------------------------------------------------
+sub odd_cells
+#-------------------------------------------------------------------------------
+{
+ my ($row, $col, $positions) = @_;
+ my @matrix;
+ push @matrix, [(0) x $col] for 1 .. $row;
+
+ for my $coord (@$positions)
+ {
+ ++$matrix[ $coord->[0] ][$_] for 0 .. $col - 1;
+ ++$matrix[$_][ $coord->[1] ] for 0 .. $row - 1;
+ }
+
+ my $odd = 0;
+
+ for my $i (0 .. $row - 1)
+ {
+ for my $j (0 .. $col - 1)
+ {
+ ++$odd unless $matrix[$i][$j] % 2 == 0;
+ }
+ }
+
+ return $odd;
+}
+
+#-------------------------------------------------------------------------------
+sub parse_input
+#-------------------------------------------------------------------------------
+{
+ my ($row, $col, @coords) = @_;
+
+ for ($row, $col, @coords)
+ {
+ / ^ $RE{num}{int} $ /x or error( qq["$_" is not a valid integer] );
+ }
+
+ $row > 0 or error( 'Invalid row value' );
+ $col > 0 or error( 'Invalid column value' );
+ scalar @coords % 2 == 0 or error( 'Odd number of coordinates' );
+
+ my @positions;
+ my $it = natatime 2, @coords;
+
+ while (my @c = $it->())
+ {
+ 0 <= $c[0] <= $row or error( 'Invalid row coordinate ' . $c[0] );
+ 0 <= $c[1] <= $col or error( 'Invalid column coordinate ' . $c[1] );
+
+ push @positions, [ @c ];
+ }
+
+ return ($row, $col, \@positions);
+}
+
+#-------------------------------------------------------------------------------
+sub run_tests
+#-------------------------------------------------------------------------------
+{
+ print "Running the test suite\n";
+
+ while (my $line = <DATA>)
+ {
+ chomp $line;
+
+ my ($test_name, $row, $col, $positions_str, $expected) =
+ split / \| /x, $line;
+
+ for ($test_name, $row, $col, $positions_str, $expected)
+ {
+ s/ ^ \s+ //x;
+ s/ \s+ $ //x;
+ }
+
+ my @coordinates = split / \s+ | , /x, $positions_str;
+ my $positions;
+ ($row, $col, $positions) = parse_input( $row, $col, @coordinates );
+ my $odd = odd_cells( $row, $col, $positions );
+
+ is $odd, $expected, $test_name;
+ }
+
+ done_testing;
+}
+
+#-------------------------------------------------------------------------------
+sub error
+#-------------------------------------------------------------------------------
+{
+ my ($message) = @_;
+
+ die "ERROR: $message\n$USAGE";
+}
+
+################################################################################
+
+__DATA__
+Example 1|2|3|0,1 1,1 |6
+Example 2|2|2|1,1 0,0 |0
+Example 3|3|3|0,0 1,2 2,1 |0
+Example 4|1|5|0,2 0,4 |2
+Example 5|4|2|1,0 3,1 2,0 0,1|8
+Minimal |1|1| |0
diff --git a/challenge-337/athanasius/raku/ch-1.raku b/challenge-337/athanasius/raku/ch-1.raku
new file mode 100644
index 0000000000..acf556d3f8
--- /dev/null
+++ b/challenge-337/athanasius/raku/ch-1.raku
@@ -0,0 +1,187 @@
+use v6d;
+
+################################################################################
+=begin comment
+
+Perl Weekly Challenge 337
+=========================
+
+TASK #1
+-------
+*Smaller Than Current*
+
+Submitted by: Mohammad Sajid Anwar
+
+You are given an array of numbers, @num1.
+
+Write a script to return an array, @num2, where $num2[i] is the count of all
+numbers less than or equal to $num1[i].
+
+Example 1
+
+ Input: @num1 = (6, 5, 4, 8)
+ Output: (2, 1, 0, 3)
+
+ index 0: numbers <= 6 are 5, 4 => 2
+ index 1: numbers <= 5 are 4 => 1
+ index 2: numbers <= 4, none => 0
+ index 3: numbers <= 8 are 6, 5, 4 => 3
+
+Example 2
+
+ Input: @num1 = (7, 7, 7, 7)
+ Output: (3, 3, 3, 3)
+
+Example 3
+
+ Input: @num1 = (5, 4, 3, 2, 1)
+ Output: (4, 3, 2, 1, 0)
+
+Example 4
+
+ Input: @num1 = (-1, 0, 3, -2, 1)
+ Output: (1, 2, 4, 0, 3)
+
+Example 5
+
+ Input: @num1 = (0, 1, 1, 2, 0)
+ Output: (1, 3, 3, 4, 1)
+
+=end comment
+################################################################################
+
+#--------------------------------------#
+# Copyright © 2025 PerlMonk Athanasius #
+#--------------------------------------#
+
+#===============================================================================
+=begin comment
+
+Assumptions
+-----------
+1. The input numbers are integers.
+2. The Task should read:
+
+ Write a script to return an array, @num2, where $num2[i] is the count of
+ all *other* numbers less than or equal to $num1[i].
+
+Interface
+---------
+1. If no command-line arguments are given, the test suite is run. Otherwise:
+2. A non-empty list of integers is entered on the command-line.
+3. If the first integer is negative, it must be preceded by "--" to indicate
+ that it is not a command-line flag.
+
+=end comment
+#===============================================================================
+
+use Test;
+
+#-------------------------------------------------------------------------------
+BEGIN
+#-------------------------------------------------------------------------------
+{
+ "\nChallenge 337, Task #1: Smaller Than Current (Raku)\n".put;
+}
+
+#===============================================================================
+multi sub MAIN
+(
+ #| A non-empty list of integers
+
+ *@num1 where { .elems > 0 && .all ~~ Int:D }
+)
+#===============================================================================
+{
+ "Input: \@num1 = (%s)\n".printf: @num1.join: ', ';
+
+ my UInt @num2 = smaller-than-current( @num1 );
+
+ "Output: (%s)\n"\ .printf: @num2.join: ', ';
+}
+
+#===============================================================================
+multi sub MAIN() # No input: run the test suite
+#===============================================================================
+{
+ run-tests();
+}
+
+#-------------------------------------------------------------------------------
+sub smaller-than-current( List:D[Int:D] $num1 --> List:D[UInt:D] )
+#-------------------------------------------------------------------------------
+{
+ my UInt %freq{Int};
+ ++%freq{$_} for @$num1;
+
+ my Int @keys = %freq.keys.sort;
+ my UInt $sum = 0;
+ my UInt %cum-freq{Int};
+
+ for @keys -> Int $key
+ {
+ $sum += %freq{$key};
+ %cum-freq{$key} = $sum;
+ }
+
+ my UInt @num2;
+
+ for @$num1 -> Int $num
+ {
+ @num2.push: %cum-freq{$num} - 1;
+ }
+
+ return @num2;
+}
+
+#-------------------------------------------------------------------------------
+sub run-tests()
+#-------------------------------------------------------------------------------
+{
+ 'Running the test suite'.put;
+
+ for test-data.lines -> Str $line
+ {
+ my Str ($test-name, $num1-str, $expd-str) = $line.split: / \| /;
+
+ for $test-name, $num1-str, $expd-str
+ {
+ s/ ^ \s+ //;
+ s/ \s+ $ //;
+ }
+
+ my Int @num1 = $num1-str.split( / \s+ /, :skip-empty ).map: { .Int };
+ my UInt @num2 = smaller-than-current( @num1 );
+ my UInt @expd = $expd-str.split( / \s+ /, :skip-empty ).map: { .Int };
+
+ is-deeply @num2, @expd, $test-name;
+ }
+
+ done-testing;
+}
+
+#-------------------------------------------------------------------------------
+sub USAGE()
+#-------------------------------------------------------------------------------
+{
+ my Str $usage = $*USAGE;
+
+ $usage ~~ s:g/ ($*PROGRAM-NAME) /raku $0/;
+
+ $usage.put;
+}
+
+#-------------------------------------------------------------------------------
+sub test-data( --> Str:D )
+#-------------------------------------------------------------------------------
+{
+ return q:to/END/;
+ Example 1| 6 5 4 8 |2 1 0 3
+ Example 2| 7 7 7 7 |3 3 3 3
+ Example 3| 5 4 3 2 1|4 3 2 1 0
+ Example 4|-1 0 3 -2 1|1 2 4 0 3
+ Example 5| 0 1 1 2 0|1 3 3 4 1
+ END
+}
+
+################################################################################
diff --git a/challenge-337/athanasius/raku/ch-2.raku b/challenge-337/athanasius/raku/ch-2.raku
new file mode 100644
index 0000000000..f3b1cd77a9
--- /dev/null
+++ b/challenge-337/athanasius/raku/ch-2.raku
@@ -0,0 +1,405 @@
+use v6d;
+
+################################################################################
+=begin comment
+
+Perl Weekly Challenge 337
+=========================
+
+TASK #2
+-------
+*Odd Matrix*
+
+Submitted by: Mohammad Sajid Anwar
+
+You are given row and col, also a list of positions in the matrix.
+
+Write a script to perform action on each location (0-indexed) as provided in the
+list and find out the total odd valued cells.
+
+For each location (r, c), do both of the following:
+
+ a) Increment by 1 all the cells on row r.
+ b) Increment by 1 all the cells on column c.
+
+Example 1
+
+ Input: $row = 2, $col = 3, @locations = ([0,1],[1,1])
+ Output: 6
+
+ Initial:
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+
+ Apply [0,1]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 ] [ 1 1 1 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ Increment col 1:
+ Before After
+ [ 1 1 1 ] [ 1 2 1 ]
+ [ 0 0 0 ] [ 0 1 0 ]
+
+ Apply [1,1]:
+ Increment row 1:
+ Before After
+ [ 1 2 1 ] [ 1 2 1 ]
+ [ 0 1 0 ] [ 1 2 1 ]
+ Increment col 1:
+ Before After
+ [ 1 2 1 ] [ 1 3 1 ]
+ [ 1 2 1 ] [ 1 3 1 ]
+
+ Final:
+ [ 1 3 1 ]
+ [ 1 3 1 ]
+
+Example 2
+
+ Input: $row = 2, $col = 2, @locations = ([1,1],[0,0])
+ Output: 0
+
+ Initial:
+ [ 0 0 ]
+ [ 0 0 ]
+
+ Apply [1,1]:
+ Increment row 1:
+ Before After
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 1 1 ]
+ Increment col 1:
+ Before After
+ [ 0 0 ] [ 0 1 ]
+ [ 1 1 ] [ 1 2 ]
+
+ Apply [0,0]:
+ Increment row 0:
+ Before After
+ [ 0 1 ] [ 1 2 ]
+ [ 1 2 ] [ 1 2 ]
+ Increment col 0:
+ Before After
+ [ 1 2 ] [ 2 2 ]
+ [ 1 2 ] [ 2 2 ]
+
+ Final:
+ [ 2 2 ]
+ [ 2 2 ]
+
+Example 3
+
+ Input: $row = 3, $col = 3, @locations = ([0,0],[1,2],[2,1])
+ Output: 0
+
+ Initial:
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+ [ 0 0 0 ]
+
+ Apply [0,0]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 ] [ 1 1 1 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ [ 0 0 0 ] [ 0 0 0 ]
+ Increment col 0:
+ Before After
+ [ 1 1 1 ] [ 2 1 1 ]
+ [ 0 0 0 ] [ 1 0 0 ]
+ [ 0 0 0 ] [ 1 0 0 ]
+
+ Apply [1,2]:
+ Increment row 1:
+ Before After
+ [ 2 1 1 ] [ 2 1 1 ]
+ [ 1 0 0 ] [ 2 1 1 ]
+ [ 1 0 0 ] [ 1 0 0 ]
+ Increment col 2:
+ Before After
+ [ 2 1 1 ] [ 2 1 2 ]
+ [ 2 1 1 ] [ 2 1 2 ]
+ [ 1 0 0 ] [ 1 0 1 ]
+
+ Apply [2,1]:
+ Increment row 2:
+ Before After
+ [ 2 1 2 ] [ 2 1 2 ]
+ [ 2 1 2 ] [ 2 1 2 ]
+ [ 1 0 1 ] [ 2 1 2 ]
+ Increment col 1:
+ Before After
+ [ 2 1 2 ] [ 2 2 2 ]
+ [ 2 1 2 ] [ 2 2 2 ]
+ [ 2 1 2 ] [ 2 2 2 ]
+
+ Final:
+ [ 2 2 2 ]
+ [ 2 2 2 ]
+ [ 2 2 2 ]
+
+Example 4
+
+ Input: $row = 1, $col = 5, @locations = ([0,2],[0,4])
+ Output: 2
+
+ Initial:
+ [ 0 0 0 0 0 ]
+
+ Apply [0,2]:
+ Increment row 0:
+ Before After
+ [ 0 0 0 0 0 ] [ 1 1 1 1 1 ]
+ Increment col 2:
+ Before After
+ [ 1 1 1 1 1 ] [ 1 1 2 1 1 ]
+
+ Apply [0,4]:
+ Increment row 0:
+ Before After
+ [ 1 1 2 1 1 ] [ 2 2 3 2 2 ]
+ Increment col 4:
+ Before After
+ [ 2 2 3 2 2 ] [ 2 2 3 2 3 ]
+
+ Final:
+ [ 2 2 3 2 3 ]
+
+Example 5
+
+ Input: $row = 4, $col = 2, @locations = ([1,0],[3,1],[2,0],[0,1])
+ Output: 8
+
+Initial:
+ [ 0 0 ]
+ [ 0 0 ]
+ [ 0 0 ]
+ [ 0 0 ]
+
+ Apply [1,0]:
+ Increment row 1:
+ Before After
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 1 1 ]
+ [ 0 0 ] [ 0 0 ]
+ [ 0 0 ] [ 0 0 ]
+ Increment col 0:
+ Before After
+ [ 0 0 ] [ 1 0 ]
+ [ 1 1 ] [ 2 1 ]
+ [ 0 0 ] [ 1 0 ]
+ [ 0 0 ] [ 1 0 ]
+
+ Apply [3,1]:
+ Increment row 3:
+ Before After
+ [ 1 0 ] [ 1 0 ]
+ [ 2 1 ] [ 2 1 ]
+ [ 1 0 ] [ 1 0 ]
+ [ 1 0 ] [ 2 1 ]
+ Increment col 1:
+ Before After
+ [ 1 0 ] [ 1 1 ]
+ [ 2 1 ] [ 2 2 ]
+ [ 1 0 ] [ 1 1 ]
+ [ 2 1 ] [ 2 2 ]
+
+ Apply [2,0]:
+ Increment row 2:
+ Before After
+ [ 1 1 ] [ 1 1 ]
+ [ 2 2 ] [ 2 2 ]
+ [ 1 1 ] [ 2 2 ]
+ [ 2 2 ] [ 2 2 ]
+ Increment col 0:
+ Before After
+ [ 1 1 ] [ 2 1 ]
+ [ 2 2 ] [ 3 2 ]
+ [ 2 2 ] [ 3 2 ]
+ [ 2 2 ] [ 3 2 ]
+
+ Apply [0,1]:
+ Increment row 0:
+ Before After
+ [ 2 1 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ [ 3 2 ] [ 3 2 ]
+ Increment col 1:
+ Before After
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+ [ 3 2 ] [ 3 3 ]
+
+ Final:
+ [ 3 3 ]
+ [ 3 3 ]
+ [ 3 3 ]
+ [ 3 3 ]
+
+=end comment
+################################################################################
+
+#--------------------------------------#
+# Copyright © 2025 PerlMonk Athanasius #
+#--------------------------------------#
+
+#===============================================================================
+=begin comment
+
+Interface
+---------
+1. If no command-line arguments are given, the test suite is run. Otherwise:
+2. Matrix dimensions (rows and columns) are entered on the command-line, follow-
+ ed by a list of coordinates describing positions within the matrix. The co-
+ ordinates are 0-indexed (row, column) integer pairs.
+
+=end comment
+#===============================================================================
+
+use Test;
+
+subset Coord of List where (UInt, UInt);
+subset Pos of Int where * > 0;
+
+#-------------------------------------------------------------------------------
+BEGIN
+#-------------------------------------------------------------------------------
+{
+ "\nChallenge 337, Task #2: Odd Matrix (Raku)\n".put;
+}
+
+#===============================================================================
+multi sub MAIN
+(
+ Pos:D $row, #= Number of matrix rows
+ Pos:D $col, #= Number of matrix columns
+
+ #| A list of matrix coordinate pairs
+
+ *@coords where { .elems %% 2 && .all ~~ UInt:D }
+)
+#===============================================================================
+{
+ "Input: \$row = $row, \$col = $col, \@locations = (%s)\n".printf:
+ @coords.rotor( 2 ).map( { '[' ~ .join( ',' ) ~ ']' } ).join: ',';
+
+ my Coord @positions;
+
+ for @coords.rotor( 2 ) -> Coord $coord
+ {
+ my UInt ($r, $c) = $coord;
+
+ $row >= $r or error( qq[Row coordinate "$r" too large] );
+ $col >= $c or error( qq[Col coordinate "$c" too large] );
+
+ @positions.push: [$r, $c];
+ }
+
+ my UInt $odd = odd-cells( $row, $col, @positions );
+
+ "Output: $odd".put;
+}
+
+#===============================================================================
+multi sub MAIN() # No input: run the test suite
+#===============================================================================
+{
+ run-tests();
+}
+
+#-------------------------------------------------------------------------------
+sub odd-cells( UInt:D $row, UInt:D $col, List:D[Coord:D] @positions --> UInt:D )
+#-------------------------------------------------------------------------------
+{
+ my Array[UInt] @matrix = Array[UInt].new( 0 xx $col ) xx $row;
+
+ for @positions -> Coord $coord
+ {
+ ++@matrix[ $coord[ 0 ]; $_ ] for 0 .. $col - 1;
+ ++@matrix[ $_; $coord[ 1 ] ] for 0 .. $row - 1;
+ }
+
+ my UInt $odd = 0;
+
+ for 0 .. $row - 1 -> UInt $i
+ {
+ for 0 .. $col - 1 -> UInt $j
+ {
+ ++$odd unless @matrix[$i; $j] %% 2;
+ }
+ }
+
+ return $odd;
+}
+
+#-------------------------------------------------------------------------------
+sub run-tests()
+#-------------------------------------------------------------------------------
+{
+ 'Running the test suite'.put;
+
+ for test-data.lines -> Str $line
+ {
+ my Str ($test-name, $row, $col, $positions-str, $expected) =
+ $line.split: / \| /;
+
+ for $test-name, $row, $col, $positions-str, $expected
+ {
+ s/ ^ \s+ //;
+ s/ \s+ $ //;
+ }
+
+ my Str @pos-strs = $positions-str.split: / \s+ /, :skip-empty;
+ my Coord @positions = @pos-strs.map:
+ {
+ Array[UInt].new:
+ .split( / \, / ).map: { .Int }
+ };
+ my UInt $odd = odd-cells( $row.Int, $col.Int, @positions );
+
+ is $odd, $expected.Int, $test-name;
+ }
+
+ done-testing;
+}
+
+#-------------------------------------------------------------------------------
+sub error( Str:D $message )
+#-------------------------------------------------------------------------------
+{
+ "ERROR: $message".put;
+
+ USAGE();
+
+ exit 0;
+}
+
+#-------------------------------------------------------------------------------
+sub USAGE()
+#-------------------------------------------------------------------------------
+{
+ my Str $usage = $*USAGE;
+
+ $usage ~~ s:g/ ($*PROGRAM-NAME) /raku $0/;
+
+ $usage.put;
+}
+
+#-------------------------------------------------------------------------------
+sub test-data( --> Str:D )
+#-------------------------------------------------------------------------------
+{
+ return q:to/END/;
+ Example 1|2|3|0,1 1,1 |6
+ Example 2|2|2|1,1 0,0 |0
+ Example 3|3|3|0,0 1,2 2,1 |0
+ Example 4|1|5|0,2 0,4 |2
+ Example 5|4|2|1,0 3,1 2,0 0,1|8
+ Minimal |1|1| |0
+ END
+}
+
+###################################