From a03991a260bac4c4cf9e79186681e190a694d49f Mon Sep 17 00:00:00 2001 From: Paulo Custodio Date: Wed, 22 Nov 2023 11:22:01 +0000 Subject: Add Forth solution --- challenge-242/paulo-custodio/forth/ch-1.fs | 8 +- challenge-244/paulo-custodio/forth/ch-1.fs | 79 ++++++++++++++++ challenge-244/paulo-custodio/forth/ch-2.fs | 145 +++++++++++++++++++++++++++++ 3 files changed, 230 insertions(+), 2 deletions(-) create mode 100644 challenge-244/paulo-custodio/forth/ch-1.fs create mode 100644 challenge-244/paulo-custodio/forth/ch-2.fs diff --git a/challenge-242/paulo-custodio/forth/ch-1.fs b/challenge-242/paulo-custodio/forth/ch-1.fs index 6de8f3a904..20fe605fd2 100644 --- a/challenge-242/paulo-custodio/forth/ch-1.fs +++ b/challenge-242/paulo-custodio/forth/ch-1.fs @@ -26,8 +26,12 @@ CREATE arr1 256 CELLS ALLOT CREATE arr2 256 CELLS ALLOT -: array_size ( arr-addr -- size-addr ) ; -: array[] ( arr-addr i -- elem-addr ) 1+ CELLS + ; +: array_size ( arr-addr -- size-addr ) +; + +: array[] ( arr-addr i -- elem-addr ) + 1+ CELLS + +; : array_push_back ( arr-addr n -- ) { arr n } diff --git a/challenge-244/paulo-custodio/forth/ch-1.fs b/challenge-244/paulo-custodio/forth/ch-1.fs new file mode 100644 index 0000000000..02010237d9 --- /dev/null +++ b/challenge-244/paulo-custodio/forth/ch-1.fs @@ -0,0 +1,79 @@ +#! /usr/bin/env gforth + +\ Challenge 244 +\ +\ Task 1: Count Smaller +\ Submitted by: Mohammad S Anwar +\ +\ You are given an array of integers. +\ +\ Write a script to calculate the number of integers smaller than the integer +\ at each index. +\ Example 1 +\ +\ Input: @int = (8, 1, 2, 2, 3) +\ Output: (4, 0, 1, 1, 3) +\ +\ For index = 0, count of elements less 8 is 4. +\ For index = 1, count of elements less 1 is 0. +\ For index = 2, count of elements less 2 is 1. +\ For index = 3, count of elements less 2 is 1. +\ For index = 4, count of elements less 3 is 3. +\ +\ Example 2 +\ +\ Input: @int = (6, 5, 4, 8) +\ Output: (2, 1, 0, 3) +\ +\ Example 3 +\ +\ Input: @int = (2, 2, 2) +\ Output: (0, 0, 0) + +CREATE nums 256 CELLS ALLOT +CREATE smaller 256 CELLS ALLOT + +: array_size ( arr-addr -- size-addr ) +; + +: array[] ( arr-addr i -- elem-addr ) + 1+ CELLS + +; + +: array_push_back ( arr-addr n -- ) + { arr n } + arr array_size @ ( size ) + arr SWAP array[] ( elem-addr ) + n SWAP ! + arr array_size 1 SWAP +! +; + +: .array ( arr -- ) + { arr } + arr array_size @ 0 ?DO + arr I array[] @ . + LOOP +; + +: collect_args ( -- ) + BEGIN NEXT-ARG DUP WHILE + 0 0 2SWAP >NUMBER 2DROP DROP + nums SWAP array_push_back + REPEAT + 2DROP +; + +: compute_smaller ( -- ) + nums array_size @ 0 ?DO + 0 ( count ) + nums array_size @ 0 ?DO + nums I array[] @ nums J array[] @ < IF 1+ THEN + LOOP + smaller SWAP array_push_back + LOOP +; + +collect_args +compute_smaller +smaller .array +BYE diff --git a/challenge-244/paulo-custodio/forth/ch-2.fs b/challenge-244/paulo-custodio/forth/ch-2.fs new file mode 100644 index 0000000000..ec3b067fc4 --- /dev/null +++ b/challenge-244/paulo-custodio/forth/ch-2.fs @@ -0,0 +1,145 @@ +#! /usr/bin/env gforth + +\ Challenge 244 +\ +\ Task 2: Group Hero +\ Submitted by: Mohammad S Anwar +\ +\ You are given an array of integers representing the strength. +\ +\ Write a script to return the sum of the powers of all possible combinations; +\ power is defined as the square of the largest number in a sequence, multiplied +\ by the smallest. +\ +\ Example 1 +\ +\ Input: @nums = (2, 1, 4) +\ Output: 141 +\ +\ Group 1: (2) => square(max(2)) * min(2) => 4 * 2 => 8 +\ Group 2: (1) => square(max(1)) * min(1) => 1 * 1 => 1 +\ Group 3: (4) => square(max(4)) * min(4) => 16 * 4 => 64 +\ Group 4: (2,1) => square(max(2,1)) * min(2,1) => 4 * 1 => 4 +\ Group 5: (2,4) => square(max(2,4)) * min(2,4) => 16 * 2 => 32 +\ Group 6: (1,4) => square(max(1,4)) * min(1,4) => 16 * 1 => 16 +\ Group 7: (2,1,4) => square(max(2,1,4)) * min(2,1,4) => 16 * 1 => 16 +\ +\ Sum: 8 + 1 + 64 + 4 + 32 + 16 + 16 => 141 + +CREATE nums 256 CELLS ALLOT +CREATE counters 256 CELLS ALLOT +CREATE combo 256 CELLS ALLOT + +: array_size ( arr-addr -- size-addr ) +; + +: array_clear ( arr-addr -- ) + 0 SWAP array_size ! +; + +: array[] ( arr-addr i -- elem-addr ) + 1+ CELLS + +; + +: array_push_back ( arr-addr n -- ) + { arr n } + arr array_size @ ( size ) + arr SWAP array[] ( elem-addr ) + n SWAP ! + arr array_size 1 SWAP +! +; + +: array_min ( arr -- n ) + { arr } + arr 0 array[] @ ( min ) + arr array_size @ 0 ?DO + arr I array[] @ MIN + LOOP +; + +: array_max ( arr -- n ) + { arr } + arr 0 array[] @ ( min ) + arr array_size @ 0 ?DO + arr I array[] @ MAX + LOOP +; + +: .array ( arr -- ) + { arr } + arr array_size @ 0 ?DO + arr I array[] @ . + LOOP +; + +: collect_args ( -- ) + BEGIN NEXT-ARG DUP WHILE + 0 0 2SWAP >NUMBER 2DROP DROP + nums SWAP array_push_back + REPEAT + 2DROP +; + +: counters_init ( k -- ) + counters array_clear + 0 ?DO + counters 0 array_push_back + LOOP +; + +: counters_increment ( -- f ) \ return false when wrapping arround + counters array_size @ 1- { i } + BEGIN i 0 >= WHILE + counters i array[] 1 SWAP +! + counters i array[] @ nums array_size @ < IF TRUE EXIT THEN + 0 counters i array[] ! + i 1- TO i + REPEAT + FALSE +; + +: counters_unique ( -- f ) \ return true if counters are all different and increasing + TRUE + counters array_size @ 1 ?DO + counters I array[] @ + counters I 1- array[] @ + <= IF DROP FALSE LEAVE THEN + LOOP +; + +: counters_select ( -- ) + combo array_clear + counters array_size @ 0 ?DO + counters I array[] @ + nums SWAP array[] @ + combo SWAP array_push_back + LOOP +; + +: array_calc_power ( arr - n ) + { arr } + arr array_max DUP * + arr array_min * +; + +: calc_power_k ( k -- n ) + counters_init + 0 ( power ) + BEGIN + counters_unique IF + counters_select combo array_calc_power + + THEN + counters_increment 0= IF EXIT THEN + AGAIN +; + +: calc_power ( -- n ) + 0 ( power ) + nums array_size @ 1+ 1 ?DO + I calc_power_k + + LOOP +; + +collect_args +calc_power . CR +BYE -- cgit