From 032b7a02321dec87671417e08a2c77931a96d9e1 Mon Sep 17 00:00:00 2001 From: Bob Lied Date: Tue, 18 Nov 2025 21:28:32 -0600 Subject: Week 348 solutions and blog --- challenge-348/bob-lied/README.md | 8 +-- challenge-348/bob-lied/blog.txt | 1 + challenge-348/bob-lied/perl/ch-1.pl | 83 +++++++++++++++++++++++++++++ challenge-348/bob-lied/perl/ch-2.pl | 101 ++++++++++++++++++++++++++++++++++++ 4 files changed, 189 insertions(+), 4 deletions(-) create mode 100644 challenge-348/bob-lied/blog.txt create mode 100644 challenge-348/bob-lied/perl/ch-1.pl create mode 100644 challenge-348/bob-lied/perl/ch-2.pl diff --git a/challenge-348/bob-lied/README.md b/challenge-348/bob-lied/README.md index 50f49b44c3..7beb100021 100644 --- a/challenge-348/bob-lied/README.md +++ b/challenge-348/bob-lied/README.md @@ -1,5 +1,5 @@ -# Solutions to weekly challenge 347 by Bob Lied +# Solutions to weekly challenge 348 by Bob Lied -## [PWC](https://perlweeklychallenge.org/blog/perl-weekly-challenge-347/) -## [GitHub](https://github.com/boblied/perlweeklychallenge-club/tree/master/challenge-347/bob-lied) -[Blog](https://dev.to/boblied/) +## [PWC](https://perlweeklychallenge.org/blog/perl-weekly-challenge-348/) +## [GitHub](https://github.com/boblied/perlweeklychallenge-club/tree/master/challenge-348/bob-lied) +[Blog](https://dev.to/boblied/pwc-348-string-alike-convert-time-3nf9) diff --git a/challenge-348/bob-lied/blog.txt b/challenge-348/bob-lied/blog.txt new file mode 100644 index 0000000000..b6b8f68b42 --- /dev/null +++ b/challenge-348/bob-lied/blog.txt @@ -0,0 +1 @@ +https://dev.to/boblied/pwc-348-string-alike-convert-time-3nf9 diff --git a/challenge-348/bob-lied/perl/ch-1.pl b/challenge-348/bob-lied/perl/ch-1.pl new file mode 100644 index 0000000000..389c5c7735 --- /dev/null +++ b/challenge-348/bob-lied/perl/ch-1.pl @@ -0,0 +1,83 @@ + +#!/usr/bin/env perl +# vim:set ts=4 sw=4 sts=4 et ai wm=0 nu: +#============================================================================= +# Copyright (c) 2025, Bob Lied +#============================================================================= +# ch-2.pl Perl Weekly Challenge 348 Task 1 String Alike +#============================================================================= +# You are given a string of even length. Write a script to find out whether +# the given string can be split into two halves of equal lengths, each with +# the same non-zero number of vowels. +# Example 1 Input: $str = "textbook" +# Output: false +# 1st half: "text" (1 vowel) 2nd half: "book" (2 vowels) +# Example 2 Input: $str = "book" +# Output: true +# 1st half: "bo" (1 vowel) 2nd half: "ok" (1 vowel) +# Example 3 Input: $str = "AbCdEfGh" +# Output: true +# 1st half: "AbCd" (1 vowel) 2nd half: "EfGh" (1 vowel) +# Example 4 Input: $str = "rhythmmyth" +# Output: false +# 1st half: "rhyth" (0 vowel) 2nd half: "mmyth" (0 vowel) +# Example 5 Input: $str = "UmpireeAudio" +# Output: false +# 1st half: "Umpire" (3 vowels) 2nd half: "eAudio" (5 vowels) +#============================================================================= + +use v5.42; +use Getopt::Long; +my $Verbose = false; +my $DoTest = false; +my $Benchmark = 0; + +GetOptions("test" => \$DoTest, "verbose" => \$Verbose, "benchmark:i" => \$Benchmark); +my $logger; +{ + use Log::Log4perl qw(:easy); + Log::Log4perl->easy_init({ level => ($Verbose ? $DEBUG : $INFO ), + layout => "%d{HH:mm:ss.SSS} %p{1} %m%n" }); + $logger = Log::Log4perl->get_logger(); +} +#============================================================================= + +exit(!runTest()) if $DoTest; +exit( runBenchmark($Benchmark) ) if $Benchmark; + +say strAlike($_) for @ARGV; + +#============================================================================= + +sub strAlike($str) +{ + $str = lc($str); + my $mid = length($str) / 2; + my @count = map { $_ =~ tr/aeiou// } + substr($str, 0, $mid), substr($str, $mid); + return $count[0] == $count[1] && $count[0] > 0; +} + + +sub runTest +{ + use Test2::V0; + + is( strAlike( "textbook"), false , "Example 1"); + is( strAlike( "book"), true , "Example 2"); + is( strAlike( "AbCEfGh"), true , "Example 3"); + is( strAlike( "rhythmmyth"), false , "Example 4"); + is( strAlike("UmpireeAudio"), false , "Example 5"); + + done_testing; +} + +sub runBenchmark($repeat) +{ + use Benchmark qw/cmpthese/; + + cmpthese($repeat, { + label => sub { }, + }); +} + diff --git a/challenge-348/bob-lied/perl/ch-2.pl b/challenge-348/bob-lied/perl/ch-2.pl new file mode 100644 index 0000000000..c510582fc7 --- /dev/null +++ b/challenge-348/bob-lied/perl/ch-2.pl @@ -0,0 +1,101 @@ +#!/usr/bin/env perl +# vim:set ts=4 sw=4 sts=4 et ai wm=0 nu: +#============================================================================= +# Copyright (c) 2025, Bob Lied +#============================================================================= +# ch-2.pl Perl Weekly Challenge 348 Task 2 Convert Time +#============================================================================= +# You are given two strings, $source and $target, containing time in 24-hour +# time form. Write a script to convert the source into target by performing +# one of the following operations: +# 1. Add 1 minute +# 2. Add 5 minutes +# 3. Add 15 minutes +# 4. Add 60 minutes +# Find the total operations needed to get to the target. +# Example 1 Input: $source = "02:30" $target = "02:45" +# Output: 1 +# Just one operation i.e. "Add 15 minutes". +# Example 2 Input: $source = "11:55" $target = "12:15" +# Output: 2 +# Two operations i.e. "Add 15 minutes" followed by "Add 5 minutes". +# Example 3 Input: $source = "09:00" $target = "13:00" +# Output: 4 +# Four operations of "Add 60 minutes". +# Example 4 Input: $source = "23:45" $target = "00:30" +# Output: 3 +# Three operations of "Add 15 minutes". +# Example 5 Input: $source = "14:20" $target = "15:25" +# Output: 2 +# Two operations, one "Add 60 minutes" and one "Add 5 minutes" +#============================================================================= + +use v5.42; + + +use Getopt::Long; +my $Verbose = false; +my $DoTest = false; +my $Benchmark = 0; + +GetOptions("test" => \$DoTest, "verbose" => \$Verbose, "benchmark:i" => \$Benchmark); +my $logger; +{ + use Log::Log4perl qw(:easy); + Log::Log4perl->easy_init({ level => ($Verbose ? $DEBUG : $INFO ), + layout => "%d{HH:mm:ss.SSS} %p{1} %m%n" }); + $logger = Log::Log4perl->get_logger(); +} +#============================================================================= + +exit(!runTest()) if $DoTest; +exit( runBenchmark($Benchmark) ) if $Benchmark; + +say convert(@ARGV); + +#============================================================================= +sub convert($source, $target) +{ + use Time::Piece; + + my $s = Time::Piece->strptime($source, "%H:%M"); + my $t = Time::Piece->strptime($target, "%H:%M"); + my $min = ($t - $s)->minutes; + if ( $min < 0 ) + { + $min += 24*60; + } + $logger->debug("src: ", $s, "\ttrg: ", $t, "\tmin=$min"); + + my $count = 0; + for my $period ( 60, 15, 5, 1 ) + { + $count += int($min / $period); + $min %= $period; + $logger->debug("$period: $count\tmin=$min"); + } + + return $count; +} + +sub runTest +{ + use Test2::V0; + + is( convert("02:30", "02:45"), 1, "Example 1"); + is( convert("11:55", "12:15"), 2, "Example 2"); + is( convert("09:00", "13:00"), 4, "Example 3"); + is( convert("23:45", "00:30"), 3, "Example 4"); + is( convert("14:20", "15:25"), 2, "Example 5"); + + done_testing; +} + +sub runBenchmark($repeat) +{ + use Benchmark qw/cmpthese/; + + cmpthese($repeat, { + label => sub { }, + }); +} -- cgit