Peter’s blog ✴ Week 329 ✴ 7 July 2025
THE WEEKLY CHALLENGE
Fun with strings
You are given a string made up of lower and upper case English letters only. Write a script to return the longest substring of the given string which is nice.
A string is nice if, for every letter of the alphabet that the string contains, it appears both in uppercase and lowercase.
Example 1 Input: $str = 'YaaAho' Output: 'aaA' Example 2 Input: $str = 'cC' Output: 'cC' Example 3 Input: $str = 'A' Output: '' No nice string found.
I chose to approach this challenge in what could be called the systematic - or boring - way.
I loop over the possible starting characters, and then over the possible lengths of substrings which are larger than the nicest substring found so far. I then check each of these for niceness, and if one is nice, I save it as the new nicest.
I chose to pull out the test for a substring being nice into a separate
subroutine is_nice() mainly to make the code clearer to read.
The post does a great job of highlighting ambiguities in specifications. It identifies potential edge cases (a9a09a) and makes reasonable assumptions while also pointing out how easily such details can be overlooked or underspecified.
This review may cover either or both challenges for this week.
#!/usr/bin/perl # Blog: http://ccgi.campbellsmiths.force9.co.uk/challenge use v5.26; # The Weekly Challenge - 2025-07-07 use utf8; # Week 329 - task 2 - Nice string use warnings; # Peter Campbell Smith binmode STDOUT, ':utf8'; use Encode; nice_string('YaaAho'); nice_string('cC'); nice_string('A'); nice_string('ABCDEedcbaZABCDEedcbaa'); # longer example my (@chars, $string); @chars = (('A' .. 'I'),('a' .. 'i')); $string .= $chars[int(rand(18))] for 0 .. 50; nice_string($string); sub nice_string { my ($string, $c, $best, $longest, $s, $t, $try); # initialise $string = shift; $c = length($string); $best = ''; $longest = 0; # loop over starting points for $s (0 .. $c - 2) { # loop up to remaining length for $t (0 .. $c - $s) { next unless $t >= $longest; $try = substr($string, $s, $t); # nicest so far? if (is_nice($try)) { $best = $try; $longest = $t; } } } say qq[\nInput: '$string']; say qq[Output: '$best']; } sub is_nice { my ($string, @chars, $c, $C); # initialise $string = shift; @chars = split('', $string); # check for nicety for $c (@chars) { $C = $c gt 'Z' ? uc($c) : lc($c); return 0 unless $string =~ m|$C|; } return 1; }
23 lines of code
Input: 'YaaAho' Output: 'aaA' Input: 'cC' Output: 'cC' Input: 'A' Output: '' Input: 'ABCDEedcbaZABCDEedcbaa' Output: 'ABCDEedcbaa' Input: 'IDbaDfiIDCDFHeEdHeFbGEGgbeBHdCAfBHbFfHIgCfiifAAI' Output: 'bGEGgbeB'
Any content of this website which has been created by Peter Campbell Smith is in the public domain