Pythagoras Primed
with Raku

by Arne Sommer

Pythagoras Primed with Raku

[418] Published 4. October 2026.

This is my response to The Weekly Challenge #393.

#393.1 Pythagoras Multiplied You are given a positive integer n.

Find the number of all positive integer triplets (a, b, c) so that a^2 + b^2 = c^2 and a, b and c are integers <= n.

Example 1:
Input: $n = 20
Output: 12

(3,4,5),  (4,3,5),   (5,12,13),(6,8,10),
(8,6,10), (8,15,17), (9,12,15),(12,5,13),
(12,9,15),(12,16,20),(15,8,17),(16,12,20)
Example 2:
Input: $n = 7
Output: 2

(3,4,5),(4,3,5)
Example 3:
Input: $n = 1
Output: 0
Example 4:
Input: $n = 15
Output: 8
Example 5:
Input: $n = 30
Output: 22

Euclid's algorithm (see e.g. en.wikipedia.org/wiki/Pythagorean_triple > "Generating a triple"), from around year 300 BC, gives us a neat way of solving this.

I have used $p instead of Wikipedia's n, as that one is used for the input. Other than that, this is just a formula to code job.

File: pythagoras-multiplied
#! /usr/bin/env raku

unit sub MAIN (UInt $n, :v(:$verbose));

my $count = 0;

for 2 .. $n.sqrt.Int -> $m
{
  for 1 ..^ $m -> $p
  {
    next unless gcd($m, $p) == 1;
    next unless ($m - $p) % 2;

    my $c = $m**2 + $p**2;
    next unless $c <= $n;

    my $a = $m**2 - $p**2;
    my $b = 2 * $m * $p;
    my $k = $n div $c;

    if $verbose
    {
      for 1 .. $k -> $i
      {
        say ": ({$a * $i}, {$b * $i}, {$c * $i}) \
          & ({$b * $i}, {$a * $i}, {$c * $i}) [i:$i]";
      }
    }

    $count += 2 * $k;
  }
}

say $count;

sub gcd(Int $a is copy, Int $b is copy)
{
  while $b
  {
    ($a, $b) = ($b, $a % $b);
  }
  $a;
}

Running it:

$ ./pythagoras-multiplied 20
12

$ ./pythagoras-multiplied 7
2

$ ./pythagoras-multiplied 1
0

$ ./pythagoras-multiplied 15
8

$ ./pythagoras-multiplied 30
22

Looking good.

With verbose mode:

$ ./pythagoras-multiplied -v 20
: (3, 4, 5) & (4, 3, 5) [i:1]
: (6, 8, 10) & (8, 6, 10) [i:2]
: (9, 12, 15) & (12, 9, 15) [i:3]
: (12, 16, 20) & (16, 12, 20) [i:4]
: (5, 12, 13) & (12, 5, 13) [i:1]
: (15, 8, 17) & (8, 15, 17) [i:1]
12

$ ./pythagoras-multiplied -v 7
: (3, 4, 5) & (4, 3, 5) [i:1]
2

$ ./pythagoras-multiplied -v 1
0

$ ./pythagoras-multiplied -v 15
: (3, 4, 5) & (4, 3, 5) [i:1]
: (6, 8, 10) & (8, 6, 10) [i:2]
: (9, 12, 15) & (12, 9, 15) [i:3]
: (5, 12, 13) & (12, 5, 13) [i:1]
8

$ ./pythagoras-multiplied -v 30
: (3, 4, 5) & (4, 3, 5) [i:1]
: (6, 8, 10) & (8, 6, 10) [i:2]
: (9, 12, 15) & (12, 9, 15) [i:3]
: (12, 16, 20) & (16, 12, 20) [i:4]
: (15, 20, 25) & (20, 15, 25) [i:5]
: (18, 24, 30) & (24, 18, 30) [i:6]
: (5, 12, 13) & (12, 5, 13) [i:1]
: (10, 24, 26) & (24, 10, 26) [i:2]
: (15, 8, 17) & (8, 15, 17) [i:1]
: (7, 24, 25) & (24, 7, 25) [i:1]
: (21, 20, 29) & (20, 21, 29) [i:1]
22

#393.2 Prime Step You are given a string with English alphabetic characters only.

What is the absolute difference of the sum of the ASCII values of the characters in the string to the nearest prime number?

Example 1:
Input: $str = "hello"
Output: 9

The ordinal values of "hello" are [104,101,108,108,111], summing up to
532. The nearest prime number to 532 is 523, resulting in an absolute difference
of 9.
Example 2:
Input: $str = "football"
Output: 2

Starting with the values [102,111,111,116,98,97,108,108] and the sum 841.
We find 839 as the nearest prime number, so the difference is 2.
Example 3:
Input: $str = "a"
Output: 0
Example 4:
Input: $str = "challenge"
Output: 2

The ordinal values of "challenge" are [99, 104, 97, 108, 108, 101, 110,
103, 101], which sum up to 931. The nearest prime number to 931 is 929, so the
difference is 2.
Example 5:
Input: $str = "perl"
Output: 2

The ordinal values of "perl" are [112, 101, 114, 108], summing up to 435.
Nearest prime is 433, so the difference is 2.
File: prime-step
#! /usr/bin/env raku

unit sub MAIN (Str $str where $str ~~ /^ <[a..zA..Z]>+ $/,
               :v(:$verbose));

my @ords  = $str.ords;
my $sum   = @ords.sum;
my $diff  = 0;
my $prime;

loop
{
  if is-prime($sum - $diff)
  {
    $prime = $sum - $diff;
    last;
  }
  if is-prime($sum + $diff)
  {
    $prime = $sum + $diff;
    last;
  }
  $diff++;
}

if $verbose
{
  say ": Ordinals: " ~ @ords.join(", ");
  say ": Sum: $sum";
  say ": Nearest prime: $prime";
}

say $diff;

[3] Ensure English letters only.

[6] Get a list of ordinal values for each character in the string with ords, the plural version of the one-character-at-a-time ord.

See docs.raku.org/routine/ords for more information about ords.

See docs.raku.org/routine/ord for more information about ord.

[7] Get the sum of those values.

[8] The difference from this sum towards the nearest prime number. We start at zero, to include the sum itself in the primeness check.

[9] The actual prime number we found.

[11] An eternal loop, with exit strategies in [16] and [21].

[13] Do we have a prime before the sum?

[15] If so, take note of the prime.

[16] and exit the loop.

[18] Do we have a prime after the sum?

[20] As [15].

[21] As [16].

[23] Increase the distance, ready for the next loop iteration.

[33] Print the difference (to the nearest prime).

Running it:

$ ./prime-step hello
9

$ ./prime-step football
2

$ ./prime-step a
0

$ ./prime-step challenge
2

$ ./prime-step perl
2

Looking good.

With verbose mode:

$ ./prime-step -v hello
: Ordinals: 104, 101, 108, 108, 111
: Sum: 532
: Nearest prime: 523
9

$ ./prime-step -v football
: Ordinals: 102, 111, 111, 116, 98, 97, 108, 108
: Sum: 851
: Nearest prime: 853
2

$ ./prime-step -v a
: Ordinals: 97
: Sum: 97
: Nearest prime: 97
0

$ ./prime-step -v challenge
: Ordinals: 99, 104, 97, 108, 108, 101, 110, 103, 101
: Sum: 931
: Nearest prime: 929
2

$ ./prime-step -v perl
: Ordinals: 112, 101, 114, 108
: Sum: 435
: Nearest prime: 433
2

And that's it.