Count the unsorted
and two thirds is enough
Weekly challenge 229 — 7 August 2023
Week 229: 7 Aug 2023
You are given three array of integers. Write a script to return all the elements that are present in at least 2 out of the 3 given arrays.
Example 1 Input: @array1 = (1, 1, 2, 4) @array2 = (2, 4) @array3 = (4) Output: (2, 4) Example 2 Input: @array1 = (4, 1) @array2 = (2, 4) @array3 = (1, 2) Output: (1, 2, 4)
My solution to this is first to construct a hash %present. I loop over the arrays using
for $j (1 .. 3)
and append $n to $present{$j} for every $n in $array$j.
So, for example 1 above, I will end up with:
$present{1} == '11' # there are 2 '1's in @array1
$present{2} == '23' # 2 is in @array2 and @array3
$present{4} == '12' # 4 is in @array1 and @array2
So now we can see that if $j appears in at least two arrays, $present{$j} will match one (or more) of '12', '13', or '23'. This will work even if $j appears more than once in a single array.
#!/usr/bin/perl use v5.16; # The Weekly Challenge - 2023-08-07 use utf8; # Week 229 task 2 - Two out of three use strict; # Peter Campbell Smith use warnings; # Blog: http://ccgi.campbellsmiths.force9.co.uk/challenge two_out_of_three([1, 1, 2, 4], [2, 4], [4]); two_out_of_three([1, 3, 2], [3, 1, 2], [2, 1, 3]); two_out_of_three([1, 2, 3], [4, 5, 6], [7, 8, 9]); # random example my ($j, @array1, @array2, @array3); for $j (0 .. 9) { push @array1, int(rand(90)); push @array2, int(rand(90)); push @array3, int(rand(90)); } two_out_of_three(\@array1, \@array2, \@array3); sub two_out_of_three { my ($j, %present, $n, $good); # for each value v in array n appends an n to present{v} for $j (1 .. 3) { $present{$_} .= $j for @{$_[$j - 1]}; } # if v is in at least two arrays, present{v} will contain 12, 23 or 13 for $n (keys %present) { $good .= qq[$n, ] if $present{$n} =~ m!12|13|23!; } say qq[\nInput: \@array1 = (], join(', ', @{$_[0]}) . qq[)] . qq[\n \@array2 = (], join(', ', @{$_[1]}) . qq[)] . qq[\n \@array3 = (], join(', ', @{$_[2]}) . qq[)]; say qq[Output: (] . ($good ? substr($good, 0, -2) : 'none') . qq[)]; }
Input: @array1 = (1, 1, 2, 4) @array2 = (2, 4) @array3 = (4) Output: (4, 2) Input: @array1 = (1, 3, 2) @array2 = (3, 1, 2) @array3 = (2, 1, 3) Output: (2, 1, 3) Input: @array1 = (1, 2, 3) @array2 = (4, 5, 6) @array3 = (7, 8, 9) Output: (none) Input: @array1 = (21, 46, 63, 64, 86, 51, 23, 35, 29, 43) @array2 = (41, 28, 54, 72, 38, 7, 2, 6, 53, 19) @array3 = (34, 76, 9, 72, 47, 51, 53, 36, 75, 14) Output: (53, 72, 51)
Any content of this website which has been created by Peter Campbell Smith is in the public domain