From 17318056ef16c5023659f4e2128c0d68d5f0d050 Mon Sep 17 00:00:00 2001 From: rir Date: Sat, 9 Jul 2022 00:24:39 -0400 Subject: 172 --- challenge-172/0rir/raku/ch-1.raku | 76 ++++++++++++++++++++++++++++++++ challenge-172/0rir/raku/ch-2.raku | 91 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 167 insertions(+) create mode 100644 challenge-172/0rir/raku/ch-1.raku create mode 100644 challenge-172/0rir/raku/ch-2.raku diff --git a/challenge-172/0rir/raku/ch-1.raku b/challenge-172/0rir/raku/ch-1.raku new file mode 100644 index 0000000000..507c548593 --- /dev/null +++ b/challenge-172/0rir/raku/ch-1.raku @@ -0,0 +1,76 @@ +#!/usr/bin/env raku +# :vim ft=raku sw=4 expandtab # ∅ ≡ ∩ ≢ +use v6.d; +use lib $?FILE.IO.parent(2).add("lib"); +use Test; +use Prime::Factor; + +=begin comment +Task 1: Prime Partition Submitted by: Mohammad S Anwar +Given two positive integers, $m and $n, find out the Prime Partition +of the given number. No duplicates allowed. + +Input: $m = 18, $n = 2 +Output: 5, 13 or 7, 11 +=end comment + +constant @prime = grep { .is-prime },( 2, 3, 5, (* + 2) … ∞); + +my $TEST = False; +if $TEST { + my @test = + { m=>7, n => 1, exp => [(7)],}, + { m=>9, n => 1, exp => [],}, + { m=>14, n => 2, exp => [(3, 11)],}, + { m=>18, n => 2, exp => [(5, 13), (7, 11)] }, + { m=>19, n => 3, exp => [(3, 5, 11), ] }, + { m=>38, n => 1, exp => [] }, + { m=>38, n => 2, exp => [( 7, 31)] }, + { m=>38, n => 3, exp => [ + (2, 5, 31), (2, 7, 29), (2, 13, 23), (2, 17, 19),]}, + { m=>38, n => 4, exp => [ + (3,5,7,23), (3,5,11,19), (3,5,13,17), (3,7,11,17),] + }, + { m=>38, n => 5, exp => [ (2,3,5,11,17 ),(2,5,7,11,13)]}, + { m=>38, n => 6, exp => [] }, + ; + plan @test.elems; + + for @test -> %h { + my @got = no-dup-prime-parts(%h, %h); + # XXX tests rely on ordering by .combinations being defined: + # step through got vs exp.any + is @got, %h, "%h, %h"; + } + exit; +} + +multi sub no-dup-prime-parts( Int $n, Int $p where * == 1 --> Array) { + return [] if not $n.is-prime; + return [($n,)]; +} + +multi sub no-dup-prime-parts( Int $num where *>0, + Int $parts where *>1 --> Array) { + my ($n, $p) = ($num, $parts); + my @addend = gather for @prime { last if $_ > $n; take $_ }; + + @addend.shift if $n %% 2 == $p %% 2; # deuce not needed; + + # Could eliminate candidates in @possible by .max too great and + # by .max too small. $n - [+] @primes[ 0 .. $k+/-] and some f(n,p) + + my @ret = gather for @addend.combinations($p) { + .&take if $n == [+] @$_ + } + return @ret; +} + +sub MAIN( $n=5, $m=38) { + print "Input: \$m = $m, \$n = $n\nOutput: "; + my $out = no-dup-prime-parts( $m, $n # ??? formatting + ).map( *.join(', ') + ).join(' or '); + say $out ?? $out !! 'No match!' ; +} + diff --git a/challenge-172/0rir/raku/ch-2.raku b/challenge-172/0rir/raku/ch-2.raku new file mode 100644 index 0000000000..e1cf415d75 --- /dev/null +++ b/challenge-172/0rir/raku/ch-2.raku @@ -0,0 +1,91 @@ +#!/usr/bin/env raku +# :vim ft=raku sw=4 expandtab # ∅ ≡ ∩ ≢ +use v6.d; +use Test; + +=begin comment +Task 2: Five-number Summary Submitted by: Mohammad S Anwar +Given an array of integers, compute the five-number summary of +the given set of integers. + +Definition and example in the wikipedia page. +=end comment + +# My naive solution gives the same results as the TI-83 calc boxplot. +# (Cannot find the site that details the various methods of calculating +# a five number summary. +# Not finding any definitive information regarding sets of size < 5, and +# not personally finding results of such meaningful, the routine dies. + +# input default and response default +my @moon = 0, 0, 1, 2, 63, 61, 27, 13; +my @moon-sumry = 0, 0.5, 7.5, 44, 63; + +constant TEST = False; +if TEST { + my @std = 6, 7, 15, 36, 39, 40, 41, 42, 43, 47, 49; + my @ti83 = 6, 15, 40, 43, 49; + + my @test = + { in => @std , expect => @ti83 }, + { in => @moon , expect => @moon-sumry }, + { in => [1,2,3,4,5,6,7,8], expect => [1,2.5,4.5,6.5,8] }, + { in => [1,2,3,4,5,6,7,8,9,10,11,12], expect => [1,3.5,6.5,9.5,12] }, + { in => [1,2,3,4,5], expect => [1,1.5,3,4.5,5] }, + { in => [1,2,3,4,5,6,7,8,9], expect => [1,2.5,5,7.5,9] }, + { in => [1,2,3,4,5,6], expect => [1,2,3.5,5,6] }, + { in => [1,2,3,4,5,6,7,8,9,10], expect => [1,3,5.5,8,10] }, + { in => [1,2,3,4,5,6,7], expect => [1,2,4,6,7] }, + { in => [1,2,3,4,5,6,7,8,9,10,11], expect => [1,3,6,9,11] }, + ; + plan @test.elems; + for @test -> %h { + is naive-five-num( %h), %h, %h; + } + done-testing; + exit; +} + +sub naive-five-num( @ary --> Array) { + my $elems = @ary.elems; + die "Won't create a summary larger than dataset. NO SPEC" if $elems < 5; + my @ret; + my @n = @ary.sort; + + given $elems % 4 { + @ret[0]= @n[0]; + @ret[4]= @n[* -1]; + my $q2 = Int(@n.end ÷ 2); + my $q1 = Int( $q2 ÷ 2); + my $q3 = $q2 + $q1; + + when 0 { @ret[1..3] = 2 «R÷« + (([+] @n[$q1..$q1+1]), + ([+] @n[$q2..$q2+1]), + ([+] @n[$q3^..$q3+2])); + } + when 1 { @ret[1] = ([+] @n[$q1-1 ..$q1]) ÷ 2; + @ret[2] = @n[$q2]; + @ret[3] = ([+] @n[$q3 ..$q3+1]) ÷ 2; + } + when 2 { @ret[1..3] + = @n[$q1], ([+] @n[$q2 ..$q2+1]) ÷ 2, @n[$q3+1]; + } + when 3 { @ret[1..3] = @n[$q1], @n[$q2], @n[$q3+1]; + } + } + @ret; +} + +exit if TEST; + +sub MAIN( @arg = @moon ) { + say "Input: ", @arg.raku(); + say "Five-number Summary (TI-83ish):"; + say " ", naive-five-num( @arg ).raku; + + die "What?! That's wrong!" if + @arg eqv @moon and naive-five-num(@arg) !~~ @moon-sumry; +} + + -- cgit