### Perl Weekly Challenge: Week 172

#### Challenge 1:

Prime Partition

You are given two positive integers, `\$m and \$n`.

Write a script to find out the `Prime Partition` of the given number. No duplicates allowed.

For example,

``````Input: \$m = 18, \$n = 2
Output: 5, 13 or 7, 11

Input: \$m = 19, \$n = 3
Output: 3, 5, 11
``````

Another relatively easy week.

``````my @primes = (1 .. \$m).grep({ .is-prime });
my \$count = 0;
``````

I started the Raku version of my solution for task 1 with a list of all the prime numbers less than `\$m`. I also set up a variable to hold the number of prime partitions found for reasons I shall explain in a bit.

``````for @primes.combinations(\$n) -> @combo {
``````

Now we have a list of primes, `.combinations()` gives us a list of all the combinations of those primes with a length equal to `\$n`.

``````    if ([+] @combo) == \$m {
@combo.join(q{, }).say;
\$count++;
}
``````

If the sum (found with `[+]`) of the elements of a combination equal `\$m`, it is a prime partition. We print it out and increase `\$count` by 1.

``````}

unless \$count {
say "No such prime partition.";
}
``````

(Full code on Github.)

The spec didn't say what to do if `\$m` doesn't have any prime partitions of length `\$n` which is a distinct possibility so I added this last bit. If after examining all combinations, the value of `\$count` is still 0, we print an error message.

Below is the Perl version. Once I had provided the `combinations()`, `isPrime()`, and `sum()` functions which I had written for previous challenges, the script worked the same as the Raku version.

``````my @primes = grep { isPrime(\$_) } 1 .. \$m;
my \$count = 0;

for my \$combo (combinations(\@primes, \$n)) {
if (sum(\$combo) == \$m) {
say join q{, }, @{\$combo};
\$count++;
}
}

unless (\$count) {
say "No such prime partition.";
}
``````

(Full code on Github.)

#### Challenge 2:

Five-number Summary

You are given an array of integers.

Write a script to compute the `five-number summary` of the given set of integers.

You can find the definition and example in the wikipedia page.

``````my @nums = @args.sort;
my \$e = @nums.elems;
``````

The referenced Wikipedia page suggest sorting the array of integers into ascending order before starting but because arguments in Raku are immutable, I copied the sorted list into a new list called `@nums`. I also stored the length of the list as we will be using that value a lot.

``````say "minimum:        ", @nums.min;
``````

The minimum value of a list is easy to find with the `.min()` method.

``````say "lower quartile: ", \$e %% 2 ?? (@nums[\$e / 4 - 1] + @nums[\$e / 4]) / 2 !! @nums[\$e / 4];
say "median:         ", \$e %% 2 ?? (@nums[\$e / 2 - 1] + @nums[\$e / 2]) / 2 !! @nums[\$e / 2];
say "upper quartile: ", \$e %% 2 ?? (@nums[\$e / 4 * 3 - 1] + @nums[\$e / 4 * 3]) / 2 !! @nums[\$e / 4 * 3];
``````

For the next three values, we only need to find the elements at 25%, 50% and 75% of the `@nums` list. Hover if the list has an even number will fall between two elements so we find those, add them together and divide by 2 to get the correct answer.

``````say "maximum:        ", @nums.max;
``````

To find the maximum value of a list you merely have to use the `.max()` method.

(Full Raku code on Github.)

Barring syntactic differences, the Perl version is almost exactly the same.

``````my @nums = sort { \$a <=> \$b } @ARGV;
my \$e = scalar @nums;

say "minimum:        ", \$nums;
``````

One exception is that Perl has no `.min()` method. However because `@nums` is sorted in ascending order, the first element (i.e. `\$nums`) will always be the minimum value.

``````say "lower quartile: ", \$e % 2 == 0 ? (\$nums[\$e / 4 - 1] + \$nums[\$e / 4]) / 2 : \$nums[\$e / 4];
say "median:         ", \$e % 2 == 0 ? (\$nums[\$e / 2 - 1] + \$nums[\$e / 2]) / 2 : \$nums[\$e / 2];
say "upper quartile: ", \$e % 2 == 0 ? (\$nums[\$e / 4 * 3 - 1] + \$nums[\$e / 4 * 3]) / 2 : \$nums[\$e / 4 * 3];
say "maximum:        ", \$nums[-1];
``````

(Full Perl code on Github.)

Similiarly Perl has no `.max()` method but we know the last element (i.e. `\$nums[-1]`) will always be the maximum value.