<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" ><generator uri="https://jekyllrb.com/" version="3.10.0">Jekyll</generator><link href="http://em.fis.unam.mx/feed.xml" rel="self" type="application/atom+xml" /><link href="http://em.fis.unam.mx/" rel="alternate" type="text/html" /><updated>2026-06-08T16:19:26+00:00</updated><id>http://em.fis.unam.mx/feed.xml</id><title type="html">W. Luis Mochán. Blog.</title><subtitle>[&quot;Físico, investigador del ICF-UNAM.&quot;, &quot;Physicist, researcher at ICF-UNAM.&quot;]</subtitle><entry><title type="html">Perl Weekly Challenge 377.</title><link href="http://em.fis.unam.mx/2026/06/08/PWC377/" rel="alternate" type="text/html" title="Perl Weekly Challenge 377." /><published>2026-06-08T00:00:00+00:00</published><updated>2026-06-08T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/06/08/PWC377</id><content type="html" xml:base="http://em.fis.unam.mx/2026/06/08/PWC377/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-377/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-377/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-377">The Weekly Challenge - 377</a>.</p>

<h1 id="task-1-reverse-existence">Task 1: Reverse Existence</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a string.

Write a script to find whether any substring of length 2 is
also present in the reverse of the given string.

Example 1
Input: $str = "abcba"
Output: true

Reverse of given string is "abcba".
The substring "ab" in original string is also present in the reverse string too.
￼
Example 2
Input: $str = "racecar"
Output: true

The substring "ce" is present in both.
￼
Example 3
Input: $str = "abcd"
Output: false
￼
Example 4
Input: $str = "banana"
Output: true

The substring "an" is present in both.
￼
Example 5
Input: $str = "hello"
Output: true

The substring "ll" is present in both.
￼
</code></pre></div></div>

<p>I use a regular expression to extract all two character
subsequences, I reverse them and I test the original string
against all. Any match yields a <code class="language-plaintext highlighter-rouge">true" result. If all
attempts fail, I get a =False</code> result. The code fits a
1.5-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
L:for(@ARGV){$s=$_;$s=~/$_/&amp;&amp;(say("$s -&gt; T"),next L)for(map{"".reverse $_}
$s=~/(?=(..))/g);say "$s -&gt; F";}
' abcba racecar abcd banana hello
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>abcba -&gt; T
racecar -&gt; T
abcd -&gt; F
banana -&gt; T
hello -&gt; T
</code></pre></div></div>

<p>The full code is</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 377
 2  # Task 1:  Reverse Existence
 3  #
 4  # See https://wlmb.github.io/2026/06/08/PWC377/#task-1-reverse-existence
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV;
 7      Usage: $0 S0 S1...
 8      to test if the reversed string Sn when reversed
 9      contains a two character substring of the original string.
10      FIN
11  STRING: for my $string (@ARGV){
12      for(map{"".reverse $_}      # reverse each substring
13          $string=~/(?=(..))/g    # get all 2 char substrings
14          ){
15          say("$string -&gt; True"), next STRING
16              if $string=~/$_/;
17      }
18      say "$string -&gt; False";
19  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl abcba racecar abcd banana hello
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>abcba -&gt; True
racecar -&gt; True
abcd -&gt; False
banana -&gt; True
hello -&gt; True
</code></pre></div></div>

<h1 id="task-2-prefix-suffix">Task 2: Prefix Suffix</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given an array of strings.

Write a script to find if the two strings (str1, str2) in
the given array such that str1 is prefix and suffix of
str2. Return the total count of such pairs.

Example 1
Input: @array = ("a", "aba", "ababa", "aa")
Output: 4

$array[0], $array[1]: "a" is a prefix and suffix of "aba"
$array[0], $array[2]: "a" is a prefix and suffix of "ababa"
$array[0], $array[3]: "a" is a prefix and suffix of "aa"
$array[1], $array[2]: "aba" is a prefix and suffix of "ababa"
￼
Example 2
Input: @array = ("pa", "papa", "ma", "mama")
Output: 2

$array[0], $array[1]: "pa" is a prefix and suffix of "papa"
$array[2], $array[3]: "ma" is a prefix and suffix of "mama"
￼
Example 3
Input: @array = ("abao", "ab")
Output: 0
￼
Example 4
Input: @array = ("abab", "abab")
Output: 1

$array[0], $array[1]: "abab" is a prefix and suffix of "abab"
￼
Example 5
Input: @array = ("ab", "abab", "ababab")
Output: 3

$array[0], $array[1]: "ab" is a prefix and suffix of "abab"
$array[0], $array[2]: "ab" is a prefix and suffix of "ababab"
$array[1], $array[2]: "abab" is a prefix and suffix of "ababab"
￼
Example 6
Input: @array = ("abc", "def", "ghij")
Output: 0
￼
</code></pre></div></div>

<p>I can check if a string matches at the beginning and at the
end of each of the strings and increment a counter each
succesful match. As each string matches itself, I subtract
the number of strings. I assume the arrays are input as
space separated strings. The result fits a one-liner:</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for(@ARGV){my@s=split" ";my $c=0;for my $x(@s){/^$x/&amp;&amp;/$x$/&amp;&amp;++$c for@s};say"$_ -&gt; ",$c - @s;}
'  "a aba ababa aa" "pa papa ma mama" "abao ab" "abab abab" \
   "ab abab ababab" "abc def ghij"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a aba ababa aa -&gt; 4
pa papa ma mama -&gt; 2
abao ab -&gt; 0
abab abab -&gt; 2 *
ab abab ababab -&gt; 3
abc def ghij -&gt; 0
</code></pre></div></div>

<p>There is certain ambiguity in the problem statement: Every
string is a prefix and suffix of itself, but the examples
show that doesn’t count. However, if we are given two equal
strings <code class="language-plaintext highlighter-rouge">$s1==$s2</code> then <code class="language-plaintext highlighter-rouge">$s1</code> is a prefix and suffix of
<code class="language-plaintext highlighter-rouge">$s2</code> <strong>and</strong> <code class="language-plaintext highlighter-rouge">$s2</code> is a prefix and suffix of <code class="language-plaintext highlighter-rouge">$s1</code>. So I
expect a contribution of 2 to the count. But then, in
example 3 the expected output is 1. This is confusing, as it
could happen that <strong>three</strong> strings are equal,
<code class="language-plaintext highlighter-rouge">$s1==$s2==$s3</code>. What would the expected solution be in this
case? Even if example 3 is correct, the result is
ambiguous. There are six ordered pairs of equal strings, 3
unordered pairs, so a result of 1 or 3 would be consistent
with example 3. According to my approach,
the result would be 6 and unambiguous. Thus, I keep that approach.</p>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 377
 2  # Task 2:  Prefix Suffix
 3  #
 4  # See https://wlmb.github.io/2026/06/08/PWC377/#task-2-prefix-suffix
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV;
 7      Usage: $0 A0 A1...
 8      to find in how many pairs of space-separated substrings of the string An
 9      are the first is both prefix and suffix of the second.
10      FIN
11  
12  for(@ARGV){
13      my @strings = split" ";
14      my $count = 0;
15      for my $str1(@strings){
16          /^$str1/ &amp;&amp; /$str1$/ &amp;&amp; ++$count for @strings
17      };
18      say"$_ -&gt; ", $count - @strings;
19  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl   "a aba ababa aa" "pa papa ma mama" "abao ab" \
            "abab abab" "ab abab ababab" "abc def ghij"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a aba ababa aa -&gt; 4
pa papa ma mama -&gt; 2
abao ab -&gt; 0
abab abab -&gt; 2 *
ab abab ababab -&gt; 3
abc def ghij -&gt; 0
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Reverse Existence and Prefix Suffix]]></summary></entry><entry><title type="html">Perl Weekly Challenge 376.</title><link href="http://em.fis.unam.mx/2026/06/01/PWC376/" rel="alternate" type="text/html" title="Perl Weekly Challenge 376." /><published>2026-06-01T00:00:00+00:00</published><updated>2026-06-01T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/06/01/PWC376</id><content type="html" xml:base="http://em.fis.unam.mx/2026/06/01/PWC376/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-376/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-376/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-376">The Weekly Challenge - 376</a>.</p>

<h1 id="task-1-chessboard-squares">Task 1: Chessboard Squares</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given two coordinates of a square on 8x8 chessboard.

Write a script to find the given two coordinates have the
same colour.

8 W B W B W B W B
7 B W B W B W B W
6 W B W B W B W B
5 B W B W B W B W
4 W B W B W B W B
3 B W B W B W B W
2 W B W B W B W B
1 B W B W B W B W
  a b c d e f g h

Example 1
Input: $c1 = "a7", $c2 = "f4"
Output: true

Example 2
Input: $c1 = "c1", $c2 = "e8"
Output: false

Example 3
Input: $c1 = "b5", $c2 = "h2"
Output: false

Example 4
Input: $c1 = "f3", $c2 = "h1"
Output: true

Example 5
Input: $c1 = "a1", $c2 = "g8"
Output: false
</code></pre></div></div>

<p>Two coordinates have the same colour if the
number of horizontal and vertical steps to get from one of their
corresponding positions to the other is an even number. For example, one can reach from <code class="language-plaintext highlighter-rouge">a7</code> to
<code class="language-plaintext highlighter-rouge">f4</code> by taking <code class="language-plaintext highlighter-rouge">ord(f)-ord(a)=5</code> horizontal steps and <code class="language-plaintext highlighter-rouge">7-4=3</code> vertical steps,
and <code class="language-plaintext highlighter-rouge">5+3=8</code> is an even number. Thus, from the coordinates I have to
get the horizontal components and subtract them, get the vertical
components and subtract them, and finally, add both results and check
their divisibility by 2. The results takes a 1.5-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for my($p,$q)(@ARGV){@c=map{split""}($q,$p);@c[0,2]=map{ord}@c[0,2];say "$p $q -&gt; ",
($c[0]-$c[2]+$c[1]-$c[3])%2?"F":"T"}
' a7 f4 c1 e8 b5 h2 f3 h1 a1 g8
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a7 f4 -&gt; T
c1 e8 -&gt; F
b5 h2 -&gt; F
f3 h1 -&gt; T
a1 g8 -&gt; F
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 376
 2  # Task 1:  Chessboard Squares
 3  #
 4  # See https://wlmb.github.io/2026/06/01/PWC376/#task-1-chessboard-squares
 5  use v5.36;
 6  use feature qw(try);
 7  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 8      Usage: $0 P0 Q0 P1 Q1...
 9      to find if positions Pn Qn on a chess board have
10      the same color.
11      FIN
12  for my($p,$q)(@ARGV){
13      try {
14          do {die "Invalid position: $_" unless /^[a-h][1-8]/} for $p, $q;
15          my ($horizontalP, $verticalP, $horizontalQ, $verticalQ)
16              = map {split ""} ($p, $q);
17          ($horizontalP, $horizontalQ) = map {ord} ($horizontalP, $horizontalQ);
18          my $steps = $horizontalP-$horizontalQ+$verticalP-$verticalQ;
19          say "$p $q -&gt; ", $steps%2?"False":"True";
20      }
21      catch($e){warn $e}
22  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl a7 f4 c1 e8 b5 h2 f3 h1 a1 g8
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a7 f4 -&gt; True
c1 e8 -&gt; False
b5 h2 -&gt; False
f3 h1 -&gt; True
a1 g8 -&gt; False
</code></pre></div></div>

<h1 id="task-2-doubled-words">Task 2: Doubled Words</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Matt Martini
You are given a string (which may contain embedded newlines)
which is taken from a page on a website. The string will not
contain brackets qw{ [ ] }.

Write a script that will find doubled words (such as “this
this”) and highlight (wrap in brackets) each doubled word.

The script should:

- Work across lines, even finding situations where a word at
  the end of one line is repeated at the beginning of the
  next.

- Find doubled words despite capitalization differences,
  such as with 'The the...', as well as allow differing
  amounts of whitespace (spaces, tabs, newlines, and the
  like) to lie between the words.

- Find doubled words even when separated by HTML tags. For
  example, to make a word bold: '...it is &lt;B&gt;very&lt;/B&gt; very
  important...'. Only show lines containing doubled words.

Adapted from Mastering Regular Expressions, Third Edition by Jeffrey E. F. Friedl

Example 1
Input: $str = "you're given the job of checking the pages on a\nweb server for doubled words (such as 'this this'), a common problem\nwith documents subject to heavy editing."
Output: "web server for doubled words (such as '[this] [this]'), a common problem"

Example 2
Input: $str = "Find doubled words despite capitalization differences, such as with 'The\nthe...', as well as allow differing amounts of whitespace (spaces,\ntabs, newlines, and the like) to lie between the words."
Output: "Find doubled words despite capitalization differences, such as with '[The]\n[the]...', as well as allow differing amounts of whitespace (spaces,"

Example 3
Input: $str = "to make a word bold: '...it is &lt;B&gt;very&lt;/B&gt; very important...'."
Output: "to make a word bold: '...it is &lt;B&gt;[very]&lt;/B&gt; [very] important...'."

Example 4
Input: $str = "Perl officially stands for Practical Extraction and Report Language, except when it doesn't."
Output: ""

Example 5
Input: $str = "There's more than one one way to do it.\nEasy things should be easy and hard things should be possible."
Output: "There's more than [one] [one] way to do it."
</code></pre></div></div>

<p>I <code class="language-plaintext highlighter-rouge">split</code> the input using a capturing pattern, so I produce
an array with words and their separators: html tags, special
characters, spaces or punctuation. I can highlight
adjacent repeated words (from the examples, I guess repeated
words that are not adjacent are not to be highlighted) and
join the array to build the output. Finally, I print the
lines that contain highlighted words.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 376
 2  # Task 2:  Doubled Words
 3  #
 4  # See https://wlmb.github.io/2026/06/01/PWC376/#task-2-doubled-words
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV;
 7      Usage: $0 S0 S1...
 8      to find, highlight and print doubled words in the string Sn
 9      FIN
10  for(@ARGV){
11      my @parts=split /   # split on word separators
12         (                # capture
13          \s*             # leading spaces
14          (               # group
15            &lt;\/?\w[^&gt;]*?&gt; # html tag
16            |
17            &amp;.+?;         # html special character
18            |
19            \s            # space
20            |
21            [[:punct:]]   # punctuation
22          )+              # arbitrarily repeated
23          \s*             # trailing space
24         )
25         /xx;             # extended re syntax
26      # As there are two capture groups, @parts contains word, sep, sep, word, sep, sep...
27      for(grep{$_%3==0} 0..@parts-4){                      # for the actual words
28          next unless (lc $parts[$_] eq lc $parts[$_+3]);  # check doubled words
29          $parts[$_]="[$parts[$_]]";                       # and higlight them
30          $parts[$_+3]="[$parts[$_+3]]";
31      }
32  
33      my @lines =
34          grep {/\[/}
35          split "\n",
36          join "", @parts[
37              grep{$_%3!=2}0..@parts-1
38          ],
39          "\n";
40      say "$_\n-&gt;";
41      say $_ for @lines;
42      say "---";
43  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl \
"you're given the job of checking the pages on a
web server for doubled words (such as 'this this'), a common problem
with documents subject to heavy editing." \
"Find doubled words despite capitalization differences, such as with 'The
the...', as well as allow differing amounts of whitespace (spaces,
tabs, newlines, and the like) to lie between the words." \
"to make a word bold: '...it is &lt;B&gt;very&lt;/B&gt; very important...'." \
"Perl officially stands for Practical Extraction and Report Language, except when it doesn't." \
"There's more than one one way to do it.
Easy things should be easy and hard things should be possible."
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>you're given the job of checking the pages on a
web server for doubled words (such as 'this this'), a common problem
with documents subject to heavy editing.
-&gt;
web server for doubled words (such as '[this] [this]'), a common problem
---
Find doubled words despite capitalization differences, such as with 'The
the...', as well as allow differing amounts of whitespace (spaces,
tabs, newlines, and the like) to lie between the words.
-&gt;
Find doubled words despite capitalization differences, such as with '[The]
[the]...', as well as allow differing amounts of whitespace (spaces,
---
to make a word bold: '...it is &lt;B&gt;very&lt;/B&gt; very important...'.
-&gt;
to make a word bold: '...it is &lt;B&gt;[very]&lt;/B&gt; [very] important...'.
---
Perl officially stands for Practical Extraction and Report Language, except when it doesn't.
-&gt;
---
There's more than one one way to do it.
Easy things should be easy and hard things should be possible.
-&gt;
There's more than [one] [one] way to do it.
---
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Chessboard Squares and Doubled Words]]></summary></entry><entry><title type="html">Perl Weekly Challenge 375.</title><link href="http://em.fis.unam.mx/2026/05/26/PWC375/" rel="alternate" type="text/html" title="Perl Weekly Challenge 375." /><published>2026-05-26T00:00:00+00:00</published><updated>2026-05-26T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/05/26/PWC375</id><content type="html" xml:base="http://em.fis.unam.mx/2026/05/26/PWC375/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-375/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-375/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-375">The Weekly Challenge - 375</a>.</p>

<h1 id="task-1-single-common-word">Task 1: Single Common Word</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given two array of strings.

Write a script to return the number of strings that appear
exactly once in each of the two given arrays. String
comparison is case sensitive.

Example 1
Input: @array1 = ("apple", "banana", "cherry")
       @array2 = ("banana", "cherry", "date")
Output: 2
￼
Example 2
Input: @array1 = ("a", "ab", "abc")
       @array2 = ("a", "a", "ab", "abc")
Output: 2

"a" appears once in @array1 but appears twice in @array2,
therefore, not counted.

Example 3
Input: @array1 = ("orange", "lemon")
       @array2 = ("grape", "melon")
Output: 0

Example 4
Input: @array1 = ("test", "test", "demo")
       @array2 = ("test", "demo", "demo")
Output: 0

Example 5
Input: @array1 = ("Hello", "world")
       @array2 = ("hello", "world")
Output: 1

String comparison is case sensitive.
￼
</code></pre></div></div>

<p>I’ll assume that the arrays are provided in <code class="language-plaintext highlighter-rouge">@ARGV</code> as
space separated strings. Then I can split them, make hashes
counting the number of appearances of each string in each
array and filter the keys of one of them by checking both
counts. The result fits a simple two-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for my($x,$y)(@ARGV){my(%c,%d);$c{$_}++for split" ",$x;$d{$_}++for
split" ",$y;say"\"$x\", \"$y\" -&gt; ",0+grep{$c{$_}==$d{$_}==1}keys%c;}
' "apple banana cherry" "banana cherry date" "a ab abc" "a a ab abc" \
  "orange lemon" "grape melon" "test test demo" "test demo demo" \
  "Hello world" "hello world"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>"apple banana cherry", "banana cherry date" -&gt; 2
"a ab abc", "a a ab abc" -&gt; 2
"orange lemon", "grape melon" -&gt; 0
"test test demo", "test demo demo" -&gt; 0
"Hello world", "hello world" -&gt; 1
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 375
 2  # Task 1:  Single Common Word
 3  #
 4  # See https://wlmb.github.io/2026/05/26/PWC375/#task-1-single-common-word
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 7      Usage: $0 X0 Y0 X1 Y1...
 8      to find those space separated words that appear exactly once
 9      in strings Xn and Yn
10      FIN
11  for my ($x,$y) (@ARGV){
12      my(%count_x, %count_y);
13      $count_x{$_}++ for split " ", $x;
14      $count_y{$_}++ for split" ", $y;
15      say"\"$x\", \"$y\" -&gt; ",0+grep{($count_x{$_}//0) == ($count_y{$_}//0) == 1}
16          keys %count_x;
17  }
</code></pre></div></div>

<p>Notice that I used the <code class="language-plaintext highlighter-rouge">//</code> operator to avoid comparing
undefined values.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl "apple banana cherry" "banana cherry date" \
          "a ab abc" "a a ab abc" \
          "orange lemon" "grape melon" \
          "test test demo" "test demo demo" \
          "Hello world" "hello world"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>"apple banana cherry", "banana cherry date" -&gt; 2
"a ab abc", "a a ab abc" -&gt; 2
"orange lemon", "grape melon" -&gt; 0
"test test demo", "test demo demo" -&gt; 0
"Hello world", "hello world" -&gt; 1
</code></pre></div></div>

<h1 id="task-2-find-k-beauty">Task 2: Find K-Beauty</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a number and a digit (k).

Write a script to find the K-Beauty of the given number. The
K-Beauty of an integer number is defined as the number of
substrings of given number when it is read as a string has
length of ‘k’ and is a divisor of given number.

Example 1
Input: $num = 240, $k = 2
Output: 2

Substring with length 2:
24: 240 is divisible by 24
40: 240 is divisible by 40
￼
Example 2
Input: $num = 1020, $k = 2
Output: 3

Substring with length 2:
10: 1020 is divisible by 10
02: 1020 is divisible by 2
20: 1020 is divisible by 20
￼
Example 3
Input: $num = 444, $k = 2
Output: 0

Substring with length 2:
First "44": 444 is not divisible by 44
Second "44": 444 is not divisible by 44
￼
Example 4
Input: $num = 17, $k = 2
Output: 1

Substring with length 2:
17: 17 is divisible by 17
￼
Example 5
Input: $num = 123, $k = 1
Output: 2

Substring with length 1:
1: 123 is divisible by 1
2: 123 is not divisible by 2
3: 123 is divisible by 3
</code></pre></div></div>

<p>I use a regular expression to produce all substrings of the
given length. I filter them according to their divisibility
and then I count them. The result fits a one liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for my($n, $k)(@ARGV){say"num=$n  k=$k -&gt; ", 0+grep{$n%$_==0}$n=~/(?=(\d{$k}))/g;}
' 240 2  1020 2 444 2 17 2 123 1
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>num=240  k=2 -&gt; 2
num=1020  k=2 -&gt; 3
num=444  k=2 -&gt; 0
num=17  k=2 -&gt; 1
num=123  k=1 -&gt; 2
</code></pre></div></div>

<p>The regular expression matches and captures repeatedly (<code class="language-plaintext highlighter-rouge">/g</code>) a
sequence of <code class="language-plaintext highlighter-rouge">$k</code> digits <code class="language-plaintext highlighter-rouge">(\d{$k})</code>, but the capture is enclosed in a
zero width lookahead assertion  <code class="language-plaintext highlighter-rouge">/(?=(\d{$k}))/</code> so that the
position doesn’t advance. The <code class="language-plaintext highlighter-rouge">/g</code> modifier advances it one
step to avoid an infinite loop, so the match produces a
list of all substrings of digits of length <code class="language-plaintext highlighter-rouge">$k</code>.</p>

<p>The full code is almost identical:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 375
 2  # Task 2:  Find K-Beauty
 3  #
 4  # See https://wlmb.github.io/2026/05/26/PWC375/#task-2-find-k-beauty
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 7      Usage: $0 N0 K0 N1 K1...
 8      to find how many substrings of Nn of length Kn divide Nn.
 9      FIN
10  for my ($n, $k) (@ARGV) {
11      say"num=$n  k=$k -&gt; ", 0+grep{ $n%$_ == 0} $n=~/(?=(\d{$k}))/g;
12  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl 240 2  1020 2 444 2 17 2 123 1
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>num=240  k=2 -&gt; 2
num=1020  k=2 -&gt; 3
num=444  k=2 -&gt; 0
num=17  k=2 -&gt; 1
num=123  k=1 -&gt; 2
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Single Common Word and Find K-Beauty]]></summary></entry><entry><title type="html">Perl Weekly Challenge 374.</title><link href="http://em.fis.unam.mx/2026/05/22/PWC374/" rel="alternate" type="text/html" title="Perl Weekly Challenge 374." /><published>2026-05-22T00:00:00+00:00</published><updated>2026-05-22T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/05/22/PWC374</id><content type="html" xml:base="http://em.fis.unam.mx/2026/05/22/PWC374/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-374/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-374/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-374">The Weekly Challenge - 374</a>.</p>

<h1 id="task-1-count-vowel">Task 1: Count Vowel</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a string.

Write a script to return all possible vowel substrings in
the given string. A vowel substring is a substring that only
consists of vowels and has all five vowels present in it.

Example 1
Input: $str = "aeiou"
Output: ("aeiou")
￼
Example 2
Input: $str = "aaeeeiioouu"
Output: ("aaeeeiioou", "aaeeeiioouu", "aeeeiioou", "aeeeiioouu")

NOTE: Updated output [2025-05-18]
￼
Example 3
Input: $str = "aeiouuaxaeiou"
Output: ("aeiou", "aeiou", "eiouua", "aeiouu", "aeiouua")

NOTE: Updated output [2025-05-18]
￼
Example 4
Input: $str = "uaeiou"
Output: ("aeiou", "uaeio", "uaeiou")
￼
Example 5
Input: $str = "aeioaeioa"
Output: ()
￼
</code></pre></div></div>

<p>I can separate each string into continuous pieces with no
consonant. For each piece, I repeatedly truncate it until it
misses some vowel. The code takes a 2.5-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
sub t($x){$x=~/$_/||return 0 for(split "","aeiou");1}for(@ARGV){my@r;for my$i(/([aeiou]+)/g)
{$l=length$i;for(0..$l){t $r=substr$i,$_ or last;push @r,$r;for(1..$l){t $s=substr$r,0,-$_ or
last;push@r,$s}}}say"$_ -&gt; (@r)";}
' aeiou aaeeeiioouu aeiouuaxaeiou uaeiou aeioaeioa
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>aeiou -&gt; (aeiou)
aaeeeiioouu -&gt; (aaeeeiioouu aaeeeiioou aeeeiioouu aeeeiioou)
aeiouuaxaeiou -&gt; (aeiouua aeiouu aeiou eiouua aeiou)
uaeiou -&gt; (uaeiou uaeio aeiou)
aeioaeioa -&gt; ()
</code></pre></div></div>

<p>A slightly shorter, slightly more inefficient version is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
sub t($x){$x=~/$_/||return 0 for split"","aeiou";1}for(@ARGV){say "$_ -&gt; (", join(", ",map
{$l=length($i=$_);grep{t($_)}map{($j=$_,map {substr $j,0,-$_}(1..$l))}map{substr$i,$_}(0..$l)}
/([aeiou]+)/g), ")";}
' aeiou aaeeeiioouu aeiouuaxaeiou uaeiou aeioaeioa
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>aeiou -&gt; (aeiou)
aaeeeiioouu -&gt; (aaeeeiioouu, aaeeeiioou, aeeeiioouu, aeeeiioou)
aeiouuaxaeiou -&gt; (aeiouua, aeiouu, aeiou, eiouua, aeiou)
uaeiou -&gt; (uaeiou, uaeio, aeiou)
aeioaeioa -&gt; ()
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 374
 2  # Task 1:  Count Vowel
 3  #
 4  # See https://wlmb.github.io/2026/05/22/PWC374/#task-1-count-vowel
 5  use v5.36;
 6  use feature qw(try);
 7  die &lt;&lt;~"FIN" unless @ARGV;
 8      Usage: $0 S0 S1...
 9      to find all substrings of Sn containing only vowels, and all of them.
10      FIN
11  for(@ARGV){
12      try{
13          die "Expected a lowercase string: $_" unless $_ eq lc $_;
14          my @results;
15          for my $noconsonant(/([aeiou]+)/g){
16              my $maxlength = length $noconsonant;
17              for(0..$maxlength){
18                  # truncate from the start
19                  test(my $tentative = substr $noconsonant, $_) || last;
20                  push @results, $tentative;
21                  for(1..$maxlength){
22                      # truncate from the end
23                      test(my $truncated = substr $tentative, 0, -$_) || last;
24                      push @results, $truncated;
25                  }
26              }
27          }
28          say "$_ -&gt; (@results)";
29      }
30      catch($e){warn $e}
31  }
32  sub test($x){
33      $x=~/$_/||return 0 for(split "","aeiou");
34      return 1;
35  }
</code></pre></div></div>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl aeiou aaeeeiioouu aeiouuaxaeiou uaeiou aeioaeioa
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>aeiou -&gt; (aeiou)
aaeeeiioouu -&gt; (aaeeeiioouu aaeeeiioou aeeeiioouu aeeeiioou)
aeiouuaxaeiou -&gt; (aeiouua aeiouu aeiou eiouua aeiou)
uaeiou -&gt; (uaeiou uaeio aeiou)
aeioaeioa -&gt; ()
</code></pre></div></div>

<p>Notice that I shouldn’t worry about truncating too much, as
the test would fail anyway.</p>

<h1 id="task-2-largest-same-digits-number">Task 2: Largest Same-digits Number</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a string containing 0-9 digits only.

Write a script to return the largest number with all digits
the same in the given string.

Example 1
Input: $str = "6777133339"
Output: 3333
￼
Example 2
Input: $str = "1200034"
Output: 4
￼
Example 3
Input: $str = "44221155"
Output: 55
￼
Example 4
Input: $str = "88888"
Output: 88888
￼
Example 5
Input: $str = "11122233"
Output: 222
</code></pre></div></div>

<p>In all the examples the same digits are contiguous. Thus, I
guess I can split the string into substrings of contiguous
digits and take the largest one. This yields a half liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -MList::Util=max -E '
say "$_ -&gt; ", max /((\d)\2*)/g for(@ARGV);
' 6777133339 1200034 44221155 88888 11122233
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>6777133339 -&gt; 3333
1200034 -&gt; 4
44221155 -&gt; 55
88888 -&gt; 88888
11122233 -&gt; 222
</code></pre></div></div>

<p>Notice that <code class="language-plaintext highlighter-rouge">/((\d)\2*)/g</code> produces a list of repeated
digits alternating with the single digits that are
repeated. That doesn’t alter the result, as the single
digits are not larger than the repeated digits.</p>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 374
 2  # Task 2:  Largest Same-digits Number
 3  #
 4  # See https://wlmb.github.io/2026/05/22/PWC374/#task-2-largest-same-digits-number
 5  use v5.36;
 6  use List::Util qw(max);
 7  die &lt;&lt;~"FIN" unless @ARGV;
 8      Usage: $0 S0 S1...
 9      to find the largest number made of repetitions of
10      a single digit within the string Sn
11      FIN
12  say "$_ -&gt; ", max /((\d)\2*)/g for(@ARGV);
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl 6777133339 1200034 44221155 88888 11122233
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>6777133339 -&gt; 3333
1200034 -&gt; 4
44221155 -&gt; 55
88888 -&gt; 88888
11122233 -&gt; 222
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Count Vowel and Largest Same-digits Number]]></summary></entry><entry><title type="html">Perl Weekly Challenge 373.</title><link href="http://em.fis.unam.mx/2026/05/11/PWC373/" rel="alternate" type="text/html" title="Perl Weekly Challenge 373." /><published>2026-05-11T00:00:00+00:00</published><updated>2026-05-11T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/05/11/PWC373</id><content type="html" xml:base="http://em.fis.unam.mx/2026/05/11/PWC373/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-373/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-373/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-373">The Weekly Challenge - 373</a>.</p>

<h1 id="task-1-equal-list">Task 1: Equal List</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given two arrays of strings.

Write a script to return true if the two given array
represent the same strings otherwise false.

Example 1
Input: @arr1 = ("a", "bc")
       @arr2 = ("ab", "c")
Output: true

Array 1: "a" + "bc" = "abc"
Array 2: "ab" + "c" = "abc"

Example 2
Input: @arr1 = ("a", "b", "c")
       @arr2 = ("a", "bc")
Output: true

Array 1: "a" + "b" + "c" = "abc"
Array 2: "a" + "bc" = "abc"

Example 3
Input: @arr1 = ("a", "bc")
       @arr2 = ("a", "c", "b")
Output: false

Array 1: "a" + "bc" = "abc"
Array 2: "a" + "c" + "b" = "acb"

Example 4
Input: @arr1 = ("ab", "c", "")
       @arr2 = ("", "a", "bc")
Output: true

Array 1: "ab" + "c" + "" = "abc"
Array 2: ""  + "a" + "bc" = "abc"

Example 5
Input: @arr1 = ("p", "e", "r", "l")
       @arr2 = ("perl")
Output: true

Array 1: "p" + "e" + "r" + "l" = "perl"
Array 2: "perl"
￼
</code></pre></div></div>

<p>Well, this seems very simple. Join both sets of strings into
two strings and compare them. The result takes a one-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for my($x,$y)(@ARGV){say"$x; $y -&gt; ",f($x)eq f($y)?"T":"F";}sub f($x){join"",split/\s*,\s*/,$x}
' "a, bc" "ab, c" "a, b, c" "a, bc" "a, bc" "a, c, b" "ab, c, " ", a, bc" "p, e, r, l" "perl"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a, bc; ab, c -&gt; T
a, b, c; a, bc -&gt; T
a, bc; a, c, b -&gt; F
ab, c, ; , a, bc -&gt; T
p, e, r, l; perl -&gt; T
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 373
 2  # Task 1:  Equal List
 3  #
 4  # See https://wlmb.github.io/2026/05/11/PWC373/#task-1-equal-list
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 7      Usage: $0 S0a S0b S1a S1b ...
 8      to compare the set of comma separated strings Sna with Snb.
 9      FIN
10  
11  for my($x,$y)(@ARGV){
12      say "$x; $y -&gt; ", join_split($x) eq join_split($y)? "True":"False";
13  }
14  
15  sub join_split($x){
16      join "", split /\s*,\s*/, $x
17  }
18  
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl "a, bc"      "ab, c" \
          "a, b, c"    "a, bc" \
          "a, bc"      "a, c, b" \
          "ab, c, "    ", a, bc" \
          "p, e, r, l" "perl"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>a, bc; ab, c -&gt; True
a, b, c; a, bc -&gt; True
a, bc; a, c, b -&gt; False
ab, c, ; , a, bc -&gt; True
p, e, r, l; perl -&gt; True
</code></pre></div></div>

<h1 id="task-2-list-division">Task 2: List Division</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mark Anderson
You are given a list and a non-negative integer.

Write a script to divide the given list into given
non-negative integer equal parts. Return -1 if the integer
is more than the size of the list.

Example 1
Input: @list = (1,2,3,4,5), $n = 2
Output: ((1,2,3), (4,5))

5 / 2 = 2 remainder 1.
The extra element goes into the first chunk.

Example 2
Input: @list = (1,2,3,4,5,6), $n = 3
Output: ((1,2), (3,4), (5,6))

6 / 3 = 2 remainder 0.

Example 3
Input: @list = (1,2,3), $n = 2
Output: ((1,2), (3))

Example 4
Input: @list = (1,2,3,4,5,6,7,8,9,10), $n = 5
Output: ((1,2), (3,4), (5,6), (7,8), (9,10))

Example 5
Input: @list = (1,2,3), $n = 4
Output: -1

Example 6
Input: @list = (72,57,89,55,36,84,10,95,99,35), $n = 7;
Output: ((72,57), (89,55), (36,84), (10), (95), (99), (35))￼
</code></pre></div></div>

<p>I assume the input is a space separated list followed by the
integer. I split the list, take its size, divide it by the
integer and get the remainder. I repeatedly splice the list
joining the first <code class="language-plaintext highlighter-rouge">$n</code> elements, and adding one of the
remaining terms until they are exhausted. The code takes a
two-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for my($l,$n)(@ARGV){$s=(@l=split" ",$l)/$n; $r=@l%$n;say "$l, $n -&gt; ",
$n&gt;@l?-1:map{"(".join(" ",splice(@l,0,$s+($_&lt;=$r))).")"}(1..$n)}
' "1 2 3 4 5" 2 "1 2 3 4 5 6" 3 "1 2 3" 2 "1 2 3 4 5 6 7 8 9 10"  5 \
  "1 2 3" 4 "72 57 89 55 36 84 10 95 99 35" 7
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>1 2 3 4 5, 2 -&gt; (1 2 3)(4 5)
1 2 3 4 5 6, 3 -&gt; (1 2)(3 4)(5 6)
1 2 3, 2 -&gt; (1 2)(3)
1 2 3 4 5 6 7 8 9 10, 5 -&gt; (1 2)(3 4)(5 6)(7 8)(9 10)
1 2 3, 4 -&gt; -1
72 57 89 55 36 84 10 95 99 35, 7 -&gt; (72 57)(89 55)(36 84)(10)(95)(99)(35)
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 373
 2  # Task 2:  List Division
 3  #
 4  # See https://wlmb.github.io/2026/05/11/PWC373/#task-2-list-division
 5  use v5.36;
 6  use feature qw(try);
 7  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 8      Usage: $0 L0 N0 L1 N1...
 9      to split the space separated list Ln into Nn (almost) equal parts.
10      FIN
11  for my ($list, $pieces)(@ARGV){
12      try {
13          die "Number of pieces must be &gt;= 1: $pieces" unless $pieces &gt;= 1;
14          my @list = split " ", $list;
15          my $size = @list / $pieces;
16          my $remainder = @list % $pieces;
17          my @result = $pieces &gt; @list
18              ? -1
19              : map{
20                  "("
21                      . join(" ", splice(@list, 0, $size + ($_&lt;=$remainder)))
22                      .")"
23                } (1 .. $pieces);
24          say "$list, $pieces -&gt; @result";
25      }
26      catch($e){ warn $e }
27  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl "1 2 3 4 5" 2 "1 2 3 4 5 6" 3 "1 2 3" 2 "1 2 3 4 5 6 7 8 9 10"  5 \
          "1 2 3" 4 "72 57 89 55 36 84 10 95 99 35" 7
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>1 2 3 4 5, 2 -&gt; (1 2 3) (4 5)
1 2 3 4 5 6, 3 -&gt; (1 2) (3 4) (5 6)
1 2 3, 2 -&gt; (1 2) (3)
1 2 3 4 5 6 7 8 9 10, 5 -&gt; (1 2) (3 4) (5 6) (7 8) (9 10)
1 2 3, 4 -&gt; -1
72 57 89 55 36 84 10 95 99 35, 7 -&gt; (72 57) (89 55) (36 84) (10) (95) (99) (35)
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Equal List and List Division]]></summary></entry><entry><title type="html">Perl Weekly Challenge 372.</title><link href="http://em.fis.unam.mx/2026/05/04/PWC372/" rel="alternate" type="text/html" title="Perl Weekly Challenge 372." /><published>2026-05-04T00:00:00+00:00</published><updated>2026-05-04T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/05/04/PWC372</id><content type="html" xml:base="http://em.fis.unam.mx/2026/05/04/PWC372/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-372/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-372/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-372">The Weekly Challenge - 372</a>.</p>

<h1 id="task-1-rearrange-spaces">Task 1: Rearrange Spaces</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar

You are given a string text of words that are placed among
number of spaces.

Write a script to rearrange the spaces so that there is an
equal number of spaces between every pair of adjacent words
and that number is maximised. If you can’t distribute, place
the extra spaces at the end. Finally return the string.

Example 1
Input: $str = "  challenge  "
Output: "challenge    "

We have 4 spaces and 1 word. So all spaces go to the end.
￼
Example 2
Input: $str = "coding  is  fun"
Output: "coding  is  fun"

We have 4 spaces and 3 words (2 gaps). So 2 spaces per gap.
￼
Example 3
Input: $str = "a b c  d"
Output: "a b c d "

We have 4 spaces and 4 words (3 gaps). So 1 space per gap
and 1 remainder.
￼
Example 4
Input: $str = "  team      pwc  "
Output: "team          pwc"

We have 10 spaces and 2 words (1 gap). So 10 spaces per gap.
￼
Example 5
Input: $str = "   the  weekly  challenge  "
Output: "the    weekly    challenge "

We have 9 spaces and 3 words (2 gaps). So 4 spaces per gap
and 1 remainder.
￼
</code></pre></div></div>

<p>I can find the words by splitting on space.
The number of gaps is one less than the number of words.
The interword space is the number of spaces divided by the
number of gaps. At the end I add the residual spaces,
obtained using modular arithmetic. The code fits a two
liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for(@ARGV){$i=$_;@w=split" ";$l=0;$l+=length$1 while s/(\s+)//;($s,$r)=@w&gt;1?
($l/(@w-1),$l%(@w-1)):(0,$l);$j=" "x$s;say "\"$i\" -&gt; \"", join($j,@w)," "x$r,"\"";}
'    "  challenge  " "coding  is  fun" "a b c  d" \
     "  team      pwc  " "   the  weekly  challenge  "
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>"  challenge  " -&gt; "challenge    "
"coding  is  fun" -&gt; "coding  is  fun"
"a b c  d" -&gt; "a b c d "
"  team      pwc  " -&gt; "team          pwc"
"   the  weekly  challenge  " -&gt; "the    weekly    challenge "
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 372
 2  # Task 1:  Rearrange Spaces
 3  #
 4  # See https://wlmb.github.io/2026/05/04/PWC372/#task-1-rearrange-spaces
 5  use v5.36;
 6  die &lt;&lt;~"FIN" unless @ARGV;
 7      Usage: $0 S0 S1...
 8      to rearrange the spaces in string Sn leaving equal gaps
 9      between words.
10      FIN
11  for(@ARGV){
12      my $input = $_;
13      my @words = split" ";
14      my $length = 0;
15      $length += length $1 while s/(\s+)//;
16      my ($spaces, $rest) = @words &gt; 1
17         ? ($length / (@words-1), $length % (@words-1))
18         : (0,$length);
19      my $sep = " " x $spaces;
20      say "\"$input\" -&gt; \"", join($sep, @words), " "x$rest, "\"";
21  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl "  challenge  " "coding  is  fun" "a b c  d" \
          "  team      pwc  " "   the  weekly  challenge  "
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>"  challenge  " -&gt; "challenge    "
"coding  is  fun" -&gt; "coding  is  fun"
"a b c  d" -&gt; "a b c d "
"  team      pwc  " -&gt; "team          pwc"
"   the  weekly  challenge  " -&gt; "the    weekly    challenge "
</code></pre></div></div>

<h1 id="task-2-largest-substring">Task 2: Largest Substring</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a string.

Write a script to return the length of the largest substring
between two equal characters excluding the two
characters. Return -1 if there is no such substring.

Example 1
Input: $str = "aaaaa"
Output: 3

For character "a", we have substring "aaa".

Example 2
Input: $str = "abcdeba"
Output: 5

For character "a", we have substring "bcdeb".

Example 3
Input: $str = "abbc"
Output: 0

For character "b", we have substring "".

Example 4
Input: $str = "abcaacbc"
Output: 4

For character "a", we have substring "bca".
For character "b", we have substring "caac".
For character "c", we have substring "aacb".

Example 5
Input: $str = "laptop"
Output: 2

For character "p", we have substring "to".
</code></pre></div></div>

<p>For each character <code class="language-plaintext highlighter-rouge">$_</code> in the input, I try to match against
<code class="language-plaintext highlighter-rouge">/$_(.*)$_/</code>. If succesful, I add the length of the matched
substring to a list, and if unsuccesful I add -1. The result
is the <code class="language-plaintext highlighter-rouge">max</code> (from <code class="language-plaintext highlighter-rouge">List::Util</code>) of the list. The result
fits a one-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -MList::Util=max -E '
for(@ARGV){$i=$_;say "$_ -&gt; ", max map {$i=~m/$_(.*)$_/?length($1):-1} split "";}
' aaaaa abcdeba abbc abcaacbc laptop
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>aaaaa -&gt; 3
abcdeba -&gt; 5
abbc -&gt; 0
abcaacbc -&gt; 4
laptop -&gt; 2
</code></pre></div></div>

<p>Output: 3
Output: 5
Output: 0
Output: 4
Output: 2</p>

<p>The full code is similar. I use <code class="language-plaintext highlighter-rouge">uniq</code> from <code class="language-plaintext highlighter-rouge">List::Util</code> to
avoid redundant work.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 372
 2  # Task 2:  Largest Substring
 3  #
 4  # See https://wlmb.github.io/2026/05/04/PWC372/#task-2-largest-substring
 5  use v5.36;
 6  use List::Util qw(max uniq);
 7  die &lt;&lt;~"FIN" unless @ARGV;
 8      Usage: $0 S0 S1...
 9      to find the length of the largest substring of Sn
10      between equal characters
11      FIN
12  for(@ARGV){
13      my $input = $_;
14      say "$_ -&gt; ",
15          max
16          map {$input =~ m/$_(.*)$_/?length($1):-1;}
17          uniq
18          split "";
19  }
</code></pre></div></div>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl aaaaa abcdeba abbc abcaacbc laptop
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>aaaaa -&gt; 3
abcdeba -&gt; 5
abbc -&gt; 0
abcaacbc -&gt; 4
laptop -&gt; 2
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Rearrange Spaces and Largest Substring]]></summary></entry><entry><title type="html">Mail</title><link href="http://em.fis.unam.mx/2026/04/28/mail/" rel="alternate" type="text/html" title="Mail" /><published>2026-04-28T00:00:00+00:00</published><updated>2026-04-28T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/04/28/mail</id><content type="html" xml:base="http://em.fis.unam.mx/2026/04/28/mail/"><![CDATA[<p>How to compose and send customized emails to a list of recipients
using Perl and <code class="language-plaintext highlighter-rouge">Mail::Message</code>.</p>

<p>Yesterday I made an invitation to a concert and sent it to a longish
list of friends. To that end I made a table with the needed fields for
each correspondent and a program similar to the
following. I post them here for my own reference, but they may prove
useful to someone else.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#+name: list
</code></pre></div></div>

<table id="org0f5c9be" border="2" cellspacing="0" cellpadding="6" rules="groups" frame="hsides">


<colgroup>
<col class="org-left" />

<col class="org-left" />

<col class="org-left" />

<col class="org-left" />

<col class="org-left" />

<col class="org-left" />
</colgroup>
<thead>
<tr>
<th scope="col" class="org-left">formal </th>
<th scope="col" class="org-left">name </th>
<th scope="col" class="org-left">emails </th>
<th scope="col" class="org-left">Intro </th>
<th scope="col" class="org-left">custom </th>
<th scope="col" class="org-left">Extra </th>
</tr>
</thead>
<tbody>
<tr>
<td class="org-left">A Very Long Name </td>
<td class="org-left">Shorty </td>
<td class="org-left">&lt;s@one&gt;, &lt;s@two&gt; </td>
<td class="org-left">Hi </td>
<td class="org-left">something </td>
<td class="org-left">1 </td>
</tr>

<tr>
<td class="org-left">Prof. First Second Last </td>
<td class="org-left">Last</td>
<td class="org-left">&lt;last@address&gt;</td>
<td class="org-left">Dear Prof. </td>
<td class="org-left">anything </td>
<td class="org-left">&#xa0;</td>
</tr>
</tbody>
</table>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#+name: invite
#+begin_src perl -n :results output :var list=list

 1  use v5.36;
 2  use Mail::Message;
 3  use Encode;
 4  my $count=0;
 5  my $time=0;
 6  for($list-&gt;@*){
 7      my ($formal, $short, $emails, $intro, $custom, $extra)=@$_;
 8      my $to = "$formal $emails";
 9      my $extra_text=$extra?"You can selectively interpolate additional text\n":"";
10      my $body = decode("UTF8", &lt;&lt;~"END");
11      $Intro $name,
12      This is the main text of the email, in which I can interpolate $custom.
13      $extra_text
14      Regards,
15      Myself
16      Attachment: Some image
17      END
18  
19      my $msg = Mail::Message-&gt;build(
20  	From    =&gt; 'My Name &lt;my@address&gt;',
21  	To      =&gt; $to,
22  	Subject =&gt; 'Subject',
23  	data =&gt; $body,
24  	file =&gt; "$ENV{HOME}/path/to/image.png"
25  	);
26      $msg-&gt;send;
27      my $delta_t=1+ rand(1);
28      sleep $delta_t;
29      $time += $delta_t;
30      ++$count;
31      say "$count $time $formal";
32  }
</code></pre></div></div>

<p>I use the <code class="language-plaintext highlighter-rouge">var</code> mechanism of emacs’ <code class="language-plaintext highlighter-rouge">org-mode</code> to import the table as
a nested array reference into the program. For each line I make a
customized email. Notice that in order to attach a file such as an
image it is enough to include a line like 24. I asked <code class="language-plaintext highlighter-rouge">chatgpt</code> about
adding attachments to <code class="language-plaintext highlighter-rouge">Mail::Message</code> objects. I got several
contradictory and wrong answers, but I finally read the
manual. <code class="language-plaintext highlighter-rouge">Mail::Message</code> figures out all the mime magick. Furthermore,
I used <code class="language-plaintext highlighter-rouge">decode</code> from <code class="language-plaintext highlighter-rouge">Encode</code> in order to use UTF-8 characters such as
accented characters in the body of the message. It seems not to be
necessary for the names of the recipients nor the sender. I added some
random sleep time after each message (lines 27 and 28), actually, much
longer than shown here, in order not to abuse the network and not to
appear to be a spammer.</p>]]></content><author><name></name></author><category term="perl" /><category term="email" /><summary type="html"><![CDATA[Compose and send customized emails to a list of recipients.]]></summary></entry><entry><title type="html">Perl Weekly Challenge 371.</title><link href="http://em.fis.unam.mx/2026/04/27/PWC371/" rel="alternate" type="text/html" title="Perl Weekly Challenge 371." /><published>2026-04-27T00:00:00+00:00</published><updated>2026-04-27T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/04/27/PWC371</id><content type="html" xml:base="http://em.fis.unam.mx/2026/04/27/PWC371/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-371/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-371/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-371">The Weekly Challenge - 371</a>.</p>

<h1 id="task-1-missing-letter">Task 1: Missing Letter</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Reinier Maliepaard
You are given a sequence of 5 lowercase letters, with one
letter replaced by ‘?’. Each letter maps to its position in
the alphabet (‘a = 1’, ‘b = 2’, …, ‘z = 26’). The sequence
follows a repeating pattern of step sizes between
consecutive letters. The pattern is either a constant step
(e.g., ‘+2, +2, +2, +2’) or a simple alternating pattern of
two distinct steps (e.g., ‘+2, +3, +2, +3’).

Example 1
Input: @seq = qw(a c ? g i)
Output: e

The pattern of the sequence is +2,+2,+2,+2.
1: a
3: c
5: e
7: g
9: i
￼
Example 2
Input: @seq = qw(a d ? j m)
Output: g

The pattern of the sequence is +3,+3,+3,+3.
1: a
4: d
7: g
10: j
13: m
￼
Example 3
Input: @seq = qw(a e ? m q)
Output: i

The pattern of the sequence is +4,+4,+4,+4.
1: a
5: e
9: i
13: m
17: q
￼
Example 4
Input: @seq = qw(a c f ? k)
Output: h

The pattern of the sequence is +2,+3,+2,+3.
1: a
3: c
6: f
8: h
11: k
￼
Example 5
Input: @seq = qw(b e g ? l)
Output: j

The pattern of the sequence is +3,+2,+3,+2.
2: b
5: e
7: g
10: j
12: l
￼
</code></pre></div></div>

<p>The simple pattern, with spacing <em>m</em>, is a particular case of
the alternating pattern, with spacings <em>m</em> and <em>n</em>. Assuming the
input is well formed, I need two consecutive values to get
both n and m. For example, if the question mark is
at position 0, I can use the intervals between positions 1
and 2, and between positions 2 and 3, i.e., the intervals
starting at 1 and at 2, as they are unrelated to the unknown
element at 0. Similarly, if the question mark is
at position 2, I could use the intervals 3-4 and 0-1. Notice
that 0 and 3 have opposite parity, so they information
yielded by the two intervals is not redundant. I make
a small table to illustrate this.</p>

<table border="2" cellspacing="0" cellpadding="6" rules="groups" frame="hsides">


<colgroup>
<col class="org-right" />

<col class="org-right" />

<col class="org-right" />
</colgroup>
<thead>
<tr>
<th scope="col" class="org-right">Position of ? </th>
<th scope="col" class="org-right">Interval 1 </th>
<th scope="col" class="org-right">Interval 2 </th>
</tr>
</thead>
<tbody>
<tr>
<td class="org-right">0</td>
<td class="org-right">1-2</td>
<td class="org-right">2-3</td>
</tr>

<tr>
<td class="org-right">1</td>
<td class="org-right">2-3</td>
<td class="org-right">3-4</td>
</tr>

<tr>
<td class="org-right">2</td>
<td class="org-right">3-4</td>
<td class="org-right">0-1</td>
</tr>

<tr>
<td class="org-right">3</td>
<td class="org-right">0-1</td>
<td class="org-right">1-2</td>
</tr>

<tr>
<td class="org-right">4</td>
<td class="org-right">1-2</td>
<td class="org-right">2-3</td>
</tr>
</tbody>
</table>

<p>Notice that in all cases, if the question mark is at
position <em>k</em>, I can use the intervals starting at <em>k+1</em> and
<em>k+2</em>, both modulo 4. Finally, after finding both <em>n</em> and
<em>m</em> I can reconstruct the character at position <em>k</em> from
that at position <em>k-1</em> or that at position <em>k+1</em>. This
yields a 2-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -E '
for(@ARGV){/^(.*)\?.*$/;$k=length($1);@x=map{ord}split"";@s=map{$x[$_+1]-$x[$_]}
map{$_%4}($k+1,$k+2);say "$_ -&gt; ", chr($k?$x[$k-1]+$s[0]:$x[$k+1]-$s[1]);}
' ac?gi ad?jm ae?mq acf?k beg?l
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>ac?gi -&gt; e
ad?jm -&gt; g
ae?mq -&gt; i
acf?k -&gt; h
beg?l -&gt; j
</code></pre></div></div>

<p>For the full code I add a couple of tests.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 371
 2  # Task 1:  Missing Letter
 3  #
 4  # See https://wlmb.github.io/2026/04/27/PWC371/#task-1-missing-letter
 5  use v5.36;
 6  use feature qw(try);
 7  die &lt;&lt;~"FIN" unless @ARGV;
 8      Usage: $0 S0 S1...
 9      to find the missing letter in string Sn.
10      The strings should contain four lower case English letters a-z and
11      exactly one question mark, and they should be compatible with
12      a simple or an alternating sequence.
13      FIN
14  my $length=5;
15  for(@ARGV){
16      try {
17          die "Wrong length: $_" unless length$_ == $length;
18          die "Only lowercase English letters or question marks allowed: $_" unless /^([a-z]|\?)*$/;
19          die "Expected only one question mark: $_" if /\?(.*)\?/;
20          die "Expected a question mark: $_" unless /^(.*)\?(.*)$/;
21          my $unknown = length($1);
22          my @codes = map{ord} split "";
23          my @separations = map{$codes[$_+1]-$codes[$_]}
24                            map {$_% ($length-1)}
25                            ($unknown+1, $unknown+2);
26          my @newcodes;
27          $newcodes[0] = $unknown?$codes[0]:$codes[1]-$separations[1];
28          @newcodes[$_]=$newcodes[$_-1] + $separations[($unknown+$_)%2] for 1..$length-1;
29          die "Replacement out of range: $_" unless ord("a") &lt;= $newcodes[$unknown] &lt;= ord("z");
30          my $newstring = join "", map {chr} @newcodes;
31          my $re=s/^(.*)\?(.*)$/$1.$2/r;
32          die "Inconsistent string: $_" unless $newstring=~/$re/;
33          say "$_ -&gt; ", chr $newcodes[$unknown];
34      }
35      catch($e) { warn $e; }
36  }
</code></pre></div></div>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl ac?gi ad?jm ae?mq acf?k beg?l
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>ac?gi -&gt; e
ad?jm -&gt; g
ae?mq -&gt; i
acf?k -&gt; h
beg?l -&gt; j
</code></pre></div></div>

<p>Other examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl 2&gt;&amp;1 abc a?c AB?DE a?c?e abcde ?abcd wxyz? ab?ef
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Wrong length: abc at ./ch-1.pl line 18.
Wrong length: a?c at ./ch-1.pl line 18.
Only lowercase English letters or question marks allowed: AB?DE at ./ch-1.pl line 19.
Expected only one question mark: a?c?e at ./ch-1.pl line 20.
Expected a question mark: abcde at ./ch-1.pl line 21.
Replacement out of range: ?abcd at ./ch-1.pl line 30.
Replacement out of range: wxyz? at ./ch-1.pl line 30.
Inconsistent string: ab?ef at ./ch-1.pl line 33.
</code></pre></div></div>

<h1 id="task-2-subset-equilibrium">Task 2: Subset Equilibrium</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given an array of numbers.

Write a script to find all proper subsets with more than one
element where the sum of elements equals the sum of their
indices.

Example 1
Input: @nums = (2, 1, 4, 3)
Output: (2, 1), (1, 4), (4, 3), (2, 3)

Subset 1: (2, 1)
Values: 2 + 1 = 3
Positions: 1 + 2 = 3

Subset 2: (1, 4)
Values: 1 + 4 = 5
Positions: 2 + 3 = 5

Subset 3: (4, 3)
Values: 4 + 3 = 7
Positions: 3 + 4 = 7

Subset 4: (2, 3)
Values: 2 + 3 = 5
Positions: 1 + 4 = 5
￼
Example 2
Input: @nums = (3, 0, 3, 0)
Output: (3, 0), (3, 0, 3)

Subset 1: (3, 0)
Values: 3 + 0 = 3
Positions: 1 + 2 = 3

Subset 2: (3, 0, 3)
Values: 3 + 0 + 3 = 6
Positions: 1 + 2 + 3 = 6
￼
Example 3
Input: @nums = (5, 1, 1, 1)
Output: (5, 1, 1)

Subset 1: (5, 1, 1)
Values: 5 + 1 + 1 = 7
Positions: 1 + 2 + 4 = 7
￼
Example 4
Input: @nums = (3, -1, 4, 2)
Output: (3, 2), (3, -1, 4)

Subset 1: (3, 2)
Values: 3 + 2 = 5
Positions: 1 + 4 = 5

Subset 2: (3, -1, 4)
Values: 3 + (-1) + 4 = 6
Positions: 1 + 2 + 3 = 6
￼
Example 5
Input: @nums = (10, 20, 30, 40)
Output: ()
</code></pre></div></div>

<p>The examples show that the same numbers at different
positions are to be considered as different set elements.
There is a small notational error in example 5 above, as it
seems to imply that the empty subset is the answer, while it is
meant that the set of answers is empty. This could be fixed
by using extra parenthesis in the answers of all the
previous examples.
I use <code class="language-plaintext highlighter-rouge">subsets</code>  from <code class="language-plaintext highlighter-rouge">Algorithm::Combinatorics</code> to build
all proper subsets and I filter them to keep those that are
<em>in equilibrium</em> and have the appropriate length.
I also use <code class="language-plaintext highlighter-rouge">sum</code> from <code class="language-plaintext highlighter-rouge">List::Util</code> to
check the balance. The problem setup is based on one-based
arrays, so in Perl I have to add the number of indices to
the sum of indices. The result fits a two-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -MAlgorithm::Combinatorics=subsets -MList::Util=sum -E '
for(@ARGV){@d=split" ";@i=0..@d-1;@r=map{"[@d[@$_]]"}grep{1&lt;@$_&lt;@d
&amp;&amp;sum(@$_)+@$_==sum @d[@$_]}subsets(\@i);say"$_ -&gt; [ @r ]";}
' -- "2 1 4 3" "3 0 3 0" "5 1 1 1" "3 -1 4 2" "10 20 30 40"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>2 1 4 3 -&gt; [ [4 3] [2 3] [1 4] [2 1] ]
3 0 3 0 -&gt; [ [3 0 3] [3 0] ]
5 1 1 1 -&gt; [ [5 1 1] ]
3 -1 4 2 -&gt; [ [3 2] [3 -1 4] ]
10 20 30 40 -&gt; [  ]
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 371
 2  # Task 2:  Subset Equilibrium
 3  #
 4  # See https://wlmb.github.io/2026/04/27/PWC371/#task-2-subset-equilibrium
 5  use v5.36;
 6  use feature qw(try);
 7  use Algorithm::Combinatorics qw(subsets);
 8  use List::Util qw(all sum);
 9  use Scalar::Util qw(looks_like_number);
10  die &lt;&lt;~"FIN" unless @ARGV;
11      Usage: $0 S0 S1...
12      to find the subsets of the space separated sets of numbers
13      Sn whose sum equal the sum of their indices (one-based).
14      FIN
15  for(@ARGV){
16      try {
17          my @numbers = split " ";
18          die "Expected space separated numbers: $_"
19              unless all {looks_like_number $_} @numbers;
20          my @indices = 0..@numbers-1;
21          my @results = map{
22              "[@numbers[@$_]]"
23          } grep {
24              1 &lt; @$_ &lt; @numbers                  #check length of subset
25              &amp;&amp; sum(@$_)+@$_== sum @numbers[@$_] # check sums
26          }
27          subsets(\@indices);
28          say"$_ -&gt; [ @results ]";
29      }
30      catch($e){ warn $e; }
31  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl "2 1 4 3" "3 0 3 0" "5 1 1 1" "3 -1 4 2" "10 20 30 40"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>2 1 4 3 -&gt; [ [4 3] [2 3] [1 4] [2 1] ]
3 0 3 0 -&gt; [ [3 0 3] [3 0] ]
5 1 1 1 -&gt; [ [5 1 1] ]
3 -1 4 2 -&gt; [ [3 2] [3 -1 4] ]
10 20 30 40 -&gt; [  ]
</code></pre></div></div>

<p>Notice that if large arrays are expected, then <code class="language-plaintext highlighter-rouge">subsets</code>
can be used as an iterator, to generate and process the
subsets one by one in a loop, instead of using grep and map.</p>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Missing Letter and Subset Equilibrium]]></summary></entry><entry><title type="html">Euclidea</title><link href="http://em.fis.unam.mx/2026/04/23/euclidea/" rel="alternate" type="text/html" title="Euclidea" /><published>2026-04-23T00:00:00+00:00</published><updated>2026-04-23T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/04/23/euclidea</id><content type="html" xml:base="http://em.fis.unam.mx/2026/04/23/euclidea/"><![CDATA[<p>Problem  β-4: Find a tangent to a circle at a point.</p>

<h1 id="solution">Solution</h1>

<ol>
  <li>
    <p>Draw a circle with center at O and the given point <em>p</em>.</p>

    <p><img src="../../../../assets/images/euclidea20260423/beta4-1.svg" alt="img" /></p>
  </li>
  <li>
    <p>Draw an arbitrary point <em>q</em> on the circle.</p>

    <p><img src="../../../../assets/images/euclidea20260423/beta4-2.svg" alt="img" /></p>
  </li>
  <li>
    <p>Draw a circle centered on <em>q</em> through <em>p</em>,</p>

    <p><img src="../../../../assets/images/euclidea20260423/beta4-3.svg" alt="img" /></p>
  </li>
  <li>
    <p>This defines a second intersection <em>r</em> between the circles. Draw a
circle centered on <em>p</em> through <em>r</em>.</p>

    <p><img src="../../../../assets/images/euclidea20260423/beta4-4.svg" alt="img" /></p>
  </li>
  <li>
    <p>This intersects the second circle at <em>s</em>. Finally, the line <em>ps</em> is
the desired tangent to the first circle at <em>p</em>.</p>

    <p><img src="../../../../assets/images/euclidea20260423/beta4-5.svg" alt="img" /></p>
  </li>
</ol>

<h1 id="proof">Proof</h1>

<p>Draw the radius <em>Op</em> of the first circle and the lines <em>pr</em>, <em>pq</em>,
<em>ps</em>, <em>qr</em>, <em>qs</em>, <em>rs</em> and the angles α (<em>pOq</em>), β (<em>prq</em>), γ (<em>qpr</em>),
δ (<em>qps</em>), ε (<em>rpO</em>), and φ (<em>Oqp</em>).</p>

<p><img src="../../../../assets/images/euclidea20260423/beta4-6.svg" alt="img" /></p>

<p>As <em>p</em> and <em>q</em> are on a circle centered at <em>O</em>, and <em>r</em> is another
point  on the same circle, then β=α/2. As <em>p</em> and <em>r</em> are also in a
circle centered at <em>q</em>, the triangle <em>pqr</em> is isosceles. Therefore,
γ=β=α/2. The sides of triangle <em>pqs</em> are the same as those of <em>rqp</em>;
both triangles are congruent. Thus, δ=γ=α/2. The triangle <em>pOq</em> is
isosceles, and therefore, the angle φ =ε+γ is (π-α)/2 and
ε=π/2-α. Finally, the angle between the radius <em>Op</em> and the line
<em>ps</em> is ε+γ+δ=(π/2-α)+(α/2)+(α/2)=π/2. As <em>ps</em> is orthogonal to the
radius <em>Op</em>, it is tangent at <em>p</em> to the circle of radius <em>Op</em>, qed.</p>]]></content><author><name></name></author><category term="geometry" /><category term="euclidea" /><summary type="html"><![CDATA[Euclidea problem β-4]]></summary></entry><entry><title type="html">Perl Weekly Challenge 370.</title><link href="http://em.fis.unam.mx/2026/04/20/PWC370/" rel="alternate" type="text/html" title="Perl Weekly Challenge 370." /><published>2026-04-20T00:00:00+00:00</published><updated>2026-04-20T00:00:00+00:00</updated><id>http://em.fis.unam.mx/2026/04/20/PWC370</id><content type="html" xml:base="http://em.fis.unam.mx/2026/04/20/PWC370/"><![CDATA[<p>My solutions
(<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-370/wlmb/perl/ch-1.pl">task 1</a>
and
<a href="https://github.com/wlmb/perlweeklychallenge-club/blob/master/challenge-370/wlmb/perl/ch-2.pl">task 2</a>
)
to the  <a href="https://theweeklychallenge.org/blog/perl-weekly-challenge-370">The Weekly Challenge - 370</a>.</p>

<h1 id="task-1-popular-word">Task 1: Popular Word</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Mohammad Sajid Anwar
You are given a string paragraph and an array of the banned words.

Write a script to return the most popular word that is not
banned. It is guaranteed there is at least one word that is
not banned and the answer is unique. The words in paragraph
are case-insensitive and the answer should be in
lowercase. The words can not contain punctuation symbols.

Example 1
Input: $paragraph = "Bob hit a ball, the hit BALL flew far after it was hit."
       @banned = ("hit")
Output: "ball"

After removing punctuation and converting to lowercase, the
word "hit" appears 3 times, and "ball" appears 2 times.
Since "hit" is on the banned list, we ignore it.

Example 2
Input: $paragraph = "Apple? apple! Apple, pear, orange, pear, apple, orange."
       @banned = ("apple", "pear")
Output: "orange"

"apple"  appears 4 times.
"pear"   appears 2 times.
"orange" appears 2 times.

"apple" and "pear" are both banned.
Even though "orange" has the same frequency as "pear", it is
the only non-banned word with the highest frequency.

Example 3
Input: $paragraph = "A. a, a! A. B. b. b."
       @banned = ("b")
Output: "a"

"a" appears 4 times.
"b" appears 3 times.

The input has mixed casing and heavy punctuation.
The normalised, "a" is the clear winner, since "b" is
banned, "a" is the only choice.

Example 4
Input: $paragraph = "Ball.ball,ball:apple!apple.banana"
       @banned = ("ball")
Output: "apple"

Here the punctuation acts as a delimiter.
"ball"   appears 3 times.
"apple"  appears 2 times.
"banana" appears 1 time.

Example 5
Input: $paragraph = "The dog chased the cat, but the dog was faster than the cat."
       @banned = ("the", "dog")
Output: "cat"

"the" appears 4 times.
"dog" appears 2 times.
"cat" appears 2 times.

"chased", "but", "was", "faster", "than" appear 1 time each.
"the" is the most frequent but is banned.
"dog" is the next most frequent but is also banned.
The next most frequent non-banned word is "cat".
</code></pre></div></div>

<p>I assume @ARGV is of the form P0 B0 P1 B1… where Pn is a
paragraph and Bn a space separated list of banned
words. First I split the banned words a use them to build a
hash. I split the lowercased paragraph into (alphabetical)
words, <code class="language-plaintext highlighter-rouge">grep</code> out the valid words using the banned hash,
count the frequency of each valid word and find their
<code class="language-plaintext highlighter-rouge">max_by</code> frequency (from <code class="language-plaintext highlighter-rouge">List::UtilsBy</code>).  The result fits a two-liner.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -MList::UtilsBy=max_by -E '
for my($p,$b)(@ARGV){my(%b,%w);++$b{$_} for split" ",$b;++$w{$_}for grep
{!$b{$_}}split/[^a-z]+/,lc $p;say "p=$p b=$b -&gt; ", max_by{$w{$_}}keys %w;}
' \
"Bob hit a ball, the hit BALL flew far after it was hit." "hit" \
"Apple? apple! Apple, pear, orange, pear, apple, orange." "apple pear" \
"A. a, a! A. B. b. b." "b" \
"Ball.ball,ball:apple!apple.banana" "ball" \
"The dog chased the cat, but the dog was faster than the cat." "the dog"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>p=Bob hit a ball, the hit BALL flew far after it was hit. b=hit -&gt; ball
p=Apple? apple! Apple, pear, orange, pear, apple, orange. b=apple pear -&gt; orange
p=A. a, a! A. B. b. b. b=b -&gt; a
p=Ball.ball,ball:apple!apple.banana b=ball -&gt; apple
p=The dog chased the cat, but the dog was faster than the cat. b=the dog -&gt; cat
</code></pre></div></div>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 370
 2  # Task 1:  Popular Word
 3  #
 4  # See https://wlmb.github.io/2026/04/20/PWC370/#task-1-popular-word
 5  use v5.36;
 6  use List::UtilsBy qw(max_by);
 7  die &lt;&lt;~"FIN" unless @ARGV and @ARGV%2==0;
 8      Usage: $0 P0 B0 P1 B1...
 9      where Pn is a paragraph and Bn is a space separated list
10      if banned words, to find the most frequent permitted word
11      of each paragraph.
12      FIN
13  for my($paragraph, $banned)(@ARGV){
14      my %banned;
15      my %words;
16      ++$banned{$_} for split " ", $banned;
17      ++$words{$_} for
18          grep {!$banned{$_}}
19          split/[^a-z]+/,
20          lc $paragraph;
21      print &lt;&lt;~"END";
22          Paragraph="$paragraph";
23          banned="$banned"
24          END
25      say "    -&gt; ", max_by{$words{$_}} keys %words;
26  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-1.pl \
"Bob hit a ball, the hit BALL flew far after it was hit." "hit" \
"Apple? apple! Apple, pear, orange, pear, apple, orange." "apple pear" \
"A. a, a! A. B. b. b." "b" \
"Ball.ball,ball:apple!apple.banana" "ball" \
"The dog chased the cat, but the dog was faster than the cat." "the dog"
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Paragraph="Bob hit a ball, the hit BALL flew far after it was hit.";
banned="hit"
    -&gt; ball
Paragraph="Apple? apple! Apple, pear, orange, pear, apple, orange.";
banned="apple pear"
    -&gt; orange
Paragraph="A. a, a! A. B. b. b.";
banned="b"
    -&gt; a
Paragraph="Ball.ball,ball:apple!apple.banana";
banned="ball"
    -&gt; apple
Paragraph="The dog chased the cat, but the dog was faster than the cat.";
banned="the dog"
    -&gt; cat
</code></pre></div></div>

<h1 id="task-2-scramble-string">Task 2: Scramble String</h1>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Submitted by: Roger Bell-West
You are given two strings A and B of the same length.

Write a script to return true if string B is a scramble of
string A otherwise return false.

String B is a scramble of string A if A can be transformed
into B by a single (recursive) scramble operation.

A scramble operation is:

- If the string consists of only one character, return the string.
- Divide the string X into two non-empty parts.
- Optionally, exchange the order of those parts.
- Optionally, scramble each of those parts.
- Concatenate the scrambled parts to return a single string.

Example 1
Input: $str1 = "abc", $str2 = "acb"
Output: true

"abc"
split: ["a", "bc"]
split: ["a", ["b", "c"]]
swap: ["a", ["c", "b"]]
concatenate: "acb"

Example 2
Input: $str1 = "abcd", $str2 = "cdba"
Output: true

"abcd"
split: ["ab", "cd"]
swap: ["cd", "ab"]
split: ["cd", ["a", "b"]]
swap: ["cd", ["b", "a"]]
concatenate: "cdba"

Example 3
Input: $str1 = "hello", $str2 = "hiiii"
Output: false

A fundamental rule of scrambled strings is that they must be anagrams.

Example 4
Input: $str1 = "ateer", $str2 = "eater"
Output: true

"ateer"
split: ["ate", "er"]
split: [["at", "e"], "er"]
swap: [["e", "at"], "er"]
concatenate: "eater"

Example 5
Input: $str1 = "abcd", $str2 = "bdac"
Output: false
</code></pre></div></div>

<p>I do a recursive <code class="language-plaintext highlighter-rouge">sub</code> to check if two words are scrambled
versions of each other. The result is trivial if the strings
are identical or if they contain different sets of
letters. If not, then I split the first string into a pairs
of different lengths,
and compare each of the substrings with the correspondingly
sized substrings of the other string before and if necessary
after transposing them until I succeed. If every splitting
fails, the whole test fails. The result can be fitted to a
4-liner, not that it makes much sense.</p>

<p>Examples:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>perl -MList::Util=none -E '
for my($v,$w)(@ARGV){say "$v, $w -&gt; ",c($v, $w)?"T":"F";}sub f($x,$y,$z){substr($x,$y,$z)}sub c($v,
$w){return 1if$v eq$w;my%l;++$l{$_}for split"",$v;--$l{$_}for split"",$w;return 0unless none{$_}
values %l;my$s=length$v;for my$i(1..$s-1){return 1if(c(f($v,0,$i),f($w,0,$i))&amp;&amp;c(f($v,$i,$s-$i),
f($w,$i,$s-$i)))||(c(f($v,$i,$s-$i),f($w,0,$s-$i))&amp;&amp;c(f($v,0,$i),f($w,$s-$i,$i)));}return 0;}
' abc acb abcd cdba hello hiiii ateer eater abcd bdac
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>abc, acb -&gt; T
abcd, cdba -&gt; T
hello, hiiii -&gt; F
ateer, eater -&gt; T
abcd, bdac -&gt; F
</code></pre></div></div>

<p>By the way, trying to compact the above program I learned
that intrinsic functions such as <code class="language-plaintext highlighter-rouge">substr</code> may not be called
using the <code class="language-plaintext highlighter-rouge">goto &amp;</code> syntax nor using <code class="language-plaintext highlighter-rouge">@arrays</code> instead of
spelling out all arguments.</p>

<p>The full code is:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> 1  # Perl weekly challenge 370
 2  # Task 2:  Scramble String
 3  #
 4  # See https://wlmb.github.io/2026/04/20/PWC370/#task-2-scramble-string
 5  use v5.36;
 6  use List::Util qw(none);
 7  die &lt;&lt;~"FIN" unless @ARGV &amp;&amp; @ARGV%2==0;
 8      Usage: $0 A0 B0 A1 B1...
 9      to check if string Bn may be obtained by scrambling string An.
10      FIN
11  
12  for my ($word1, $word2)(@ARGV){
13      say "$word1, $word2 -&gt; ", check($word1, $word2)?"True":"False";
14  }
15  
16  sub check($word1, $word2){
17      return 1 if $word1 eq $word2;
18      my %letters;
19      ++$letters{$_} for split "", $word1;
20      --$letters{$_} for split "", $word2;
21      return 0 unless none {$_} values %letters;
22      my $length = length $word1;
23      for my $i(1..$length-1){
24          return 1
25              if (check(substr($word1, 0, $i), substr($word2,0,$i))
26                  &amp;&amp; check(substr($word1,$i,$length-$i), substr($word2,$i,$length-$i)))
27              || (check(substr($word1, $i, $length-$i), substr($word2,0,$length-$i))
28                  &amp;&amp; check(substr($word1,0, $i), substr($word2,$length-$i,$i)))
29              ;
30      }
31      return 0;
32  }
</code></pre></div></div>

<p>Example:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./ch-2.pl  abc acb abcd cdba hello hiiii ateer eater abcd bdac
</code></pre></div></div>

<p>Results:</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>abc, acb -&gt; True
abcd, cdba -&gt; True
hello, hiiii -&gt; False
ateer, eater -&gt; True
abcd, bdac -&gt; False
</code></pre></div></div>

<p>/;</p>]]></content><author><name></name></author><category term="pwc" /><category term="perl" /><summary type="html"><![CDATA[Popular Word and Scramble String]]></summary></entry></feed>