PERL WEEKLY CHALLENGE – 067

This is my 37th week participating into the weekly challenge.


TASK #1 › Number Combinations

Submitted by: Mohammad S Anwar

You are given two integers $m and $n. Write a script print all possible combinations of $n numbers from the list 1 2 3 … $m.

Every combination should be sorted i.e. [2,3] is valid combination but [3,2] is not.

Example:

Input: $m = 5, $n = 2

Output: [ [1,2], [1,3], [1,4], [1,5], [2,3], [2,4], [2,5], [3,4], [3,5], [4,5] ]

For this challenge, I brute forced the solution using perl’s https://metacpan.org/pod/Algorithm::Combinatorics and raku’s combinations method.

Perl 5 solution

#!/usr/bin/perl
# Test: ./ch-1.pl
use Modern::Perl;
use Algorithm::Combinatorics qw(combinations);

# Default $m and $n
my $m = shift // 5;
my $n = shift // 2;

# Answers
my @combinations = numeric_combinations($m, $n);
say answer_to_string(\@combinations);

sub numeric_combinations {
	my ($m, $n) = @_;
	my @data = (1 .. $m);

	# Possible combinations
	return my @all_combinations
		= combinations(\@data, $n);
}

# Flaten to answer array to a string
sub answer_to_string {
	my $combinations = shift;
	return
	'[ ' .
		(
			join ', ',
			map {
				'[' .
				(join ', ', @$_) .
				']'
			} @$combinations
		) .
	' ]';
}

Output: perl ./ch-1.pl

[ [1, 2], [1, 3], [1, 4], [1, 5], [2, 3], [2, 4], [2, 5], [3, 4], [3, 5], [4, 5] ]

Raku solution

# Test: perl6 ch-1.p6
multi MAIN() { MAIN(5, 2); }

multi MAIN(Int $m, Int $n) {
	my @data = (1 .. $m);
	say @data.combinations: $n;
}

Output perl6 ch-1.p6

((1 2) (1 3) (1 4) (1 5) (2 3) (2 4) (2 5) (3 4) (3 5) (4 5))

TASK #2 › Letter Phone

Submitted by: Mohammad S Anwar

You are given a digit string $S. Write a script to print all possible letter combinations that the given digit string could represent.

Letter Phone

Example:

Input: $S = '35'

Output: ["dj", "dk", "dl", "ej", "ek", "el", "fj", "fk", "fl"].

For this challenge I just brute forced to solution by splitting the first letter out of the word and using recursion to generate the possible combinations of the rest of the word.

For example ’35’ becomes:
combos(’35’)

Recursions:
‘d’ . combos(‘5’)
‘e’ . combos(‘5’)
‘d’ . combos(‘5’)

Perl 5 solution

#!/usr/bin/perl
# Test: ./ch-2.pl
use Modern::Perl;

# Default $m and $n
my $S = shift // '35';

# Phone key transations
my $phone_keys = {
	1 => ['_', ',', '@'],
	2 => ['a', 'b', 'c'],
	3 => ['d', 'e', 'f'],
	4 => ['g', 'h', 'i'],
	5 => ['j', 'k', 'l'],
	6 => ['m', 'n', 'o'],
	7 => ['p', 'q', 'r', 's'],
	8 => ['t', 'u', 'v'],
	9 => ['w', 'x', 'y', 'z'],
};

# Output the answer
say
	'[ "' .
	( join '", "',
		combos($S)
	) .
	'" ]';

# Generate the possible combinations
sub combos {
	my $S = shift;
	my @answers;

	my ($letter, $rest_of_word) =
		split('',$S,2);

	for my $l (@{$phone_keys->{$letter}}) {
		if ($rest_of_word) {
			my @partial_answers =
				combos($rest_of_word);

			push @answers,
				map { $l . $_}
				@partial_answers;
		} else {
			push @answers, $l;
		}
	}

	return @answers;
}

Output ./ch-2.pl

[ "dj", "dk", "dl", "ej", "ek", "el", "fj", "fk", "fl" ]

Raku solution

# Test: perl6 ch-1.p6

# Phone key transations
my %phone_keys = (
	'1' => ['_', ',', '@'],
	'2' => ['a', 'b', 'c'],
	'3' => ['d', 'e', 'f'],
	'4' => ['g', 'h', 'i'],
	'5' => ['j', 'k', 'l'],
	'6' => ['m', 'n', 'o'],
	'7' => ['p', 'q', 'r', 's'],
	'8' => ['t', 'u', 'v'],
	'9' => ['w', 'x', 'y', 'z'],
	'*' => ['_'],
	'0' => [''],
	'#' => [''],
);

multi MAIN() { MAIN('35'); }

multi MAIN(Str $S) {
	# Output the answer
	say combos($S).perl;
}

# Generate the possible combinations
sub combos(Str $S) {
	my @answers;

	my $letter = $S.substr(0, 1);
	my $rest_of_word = $S.substr(1);

	for (@(%phone_keys{$letter})) -> $l {
		if ($rest_of_word) {
			my @partial_answers =
				combos($rest_of_word);
			@answers.append(@partial_answers.map({ $l ~ $_ }));
		} else {
			@answers.append($l);
		}
	}

	return @answers;
}

Output perl6 ch-2.p6

["dj", "dk", "dl", "ej", "ek", "el", "fj", "fk", "fl"]

One thought on “PERL WEEKLY CHALLENGE – 067

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s