Perl Weekly Challenge 230: coming back from the mountains!
This post presents my solutions to the Perl Weekly Challenge 230.I keep doing the Perl Weekly Challenge in order to mantain my coding skills in good shape, as well as in order to learn new things, with particular regard to Raku, a language that I love.
This week, I solved the following tasks:
- PWC 230 - Task 1 - Raku
- PWC 230 - Task 2 - Raku
- PWC 230 - Task 1 in PostgreSQL PL/Perl
- PWC 230 - Task 2 in PostgreSQL PL/Perl
- PWC 230 - Task 1 in PostgreSQL PL/PgSQL
- PWC 230 - Task 2 in PostgreSQL PL/PgSQL
Raku Implementations
PWC 230 - Task 1 - Raku Implementation
The first task asked to seprate every incoming number into its digits.sub MAIN( *@nums where { @nums.elems == @nums.grep( * ~~ Int ).elems } ) {
my @digits;
@digits.push( | $_.comb ) for @nums;
@digits.join( ', ' ).say;
}
The only note here is that I need to flatten the list coming out from
comb
in order to not get nested arrays.
PWC 230 - Task 2 - Raku Implementation
The second task was about finding out which given words begin with a given prefix. Sounds like an easy job for the regular expression engine.sub MAIN( Str $prefix where { $prefix.chars >= 2 },
*@words where { @words.elems == @words.grep( * ~~ Str ).elems } ) {
my $count = 0;
$count++ if ( $_ ~~ / ^ $prefix / ) for @words;
$count.say;
}
PL/Perl Implementations
PWC 230 - Task 1 - PL/Perl Implementation
Usingsplit
it is easy to get the list of digits.
CREATE OR REPLACE FUNCTION
pwc230.task1_plperl( int[] )
RETURNS SETOF int
AS $CODE$
my ( $nums ) = @_;
for ( $nums->@* ) {
for ( split //, $_ ) {
return_next( $_ );
}
}
return undef;
$CODE$
LANGUAGE plperl;
PWC 230 - Task 2 - PL/Perl Implementation
Another quick and easy job for a regexp!CREATE OR REPLACE FUNCTION
pwc230.task2_plperl( text, text[] )
RETURNS int
AS $CODE$
my ( $prefix, $words ) = @_;
my $count = 0;
for ( $words->@* ) {
$count++ if ( $_ =~ / ^ $prefix /x );
}
return $count;
$CODE$
LANGUAGE plperl;
PostgreSQL Implementations
PWC 230 - Task 1 - PL/PgSQL Implementation
A quite straightforward approach to extract the digits into a sub array and return each of them,CREATE OR REPLACE FUNCTION
pwc230.task1_plpgsql( nums int[] )
RETURNS SETOF int
AS $CODE$
DECLARE
n int;
nn text;
BEGIN
FOREACH n IN ARRAY nums LOOP
FOREACH nn IN ARRAY regexp_split_to_array( n::text, '' ) LOOP
RETURN NEXT nn::int;
END LOOP;
END LOOP;
END
$CODE$
LANGUAGE plpgsql;
PWC 230 - Task 2 - PL/PgSQL Implementation
Regexp engine here, but checking if returns at least a result when asking for a dynamicallt built regular expression.CREATE OR REPLACE FUNCTION
pwc230.task2_plpgsql( pref text, words text[] )
RETURNS INT
AS $CODE$
DECLARE
current_word text;
counter int := 0;
BEGIN
FOREACH current_word IN ARRAY words LOOP
IF regexp_match( current_word, '^' || pref ) IS NOT NULL THEN
counter := counter + 1;
END IF;
END LOOP;
RETURN counter;
END
$CODE$
LANGUAGE plpgsql;