PERL WEEKLY CHALLENGE – 070

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


TASK #1 › Character Swapping

Submitted by: Mohammad S Anwar

You are given a string $S of size $N.

You are also given swap count $C and offset $O such that $C >= 1, $O >= 1 and $C + $O <= $N.

Write a script to perform character swapping like below:

$S[ 1 % $N ] <=> $S[ (1 + $O) % $N ]
$S[ 2 % $N ] <=> $S[ (2 + $O) % $N ]
$S[ 3 % $N ] <=> $S[ (3 + $O) % $N ]
...
...
$S[ $C % $N ] <=> $S[ ($C + $O) % $N ]

Example 1

Input:
    $S = 'perlandraku'
    $C = 3
    $O = 4

Character Swapping:
    swap 1: e <=> n = pnrlaedraku
    swap 2: r <=> d = pndlaerraku
    swap 3: l <=> r = pndraerlaku

Output:
    pndraerlaku

For this task, I just coerced the String into an array and just did some array manipulation to swap the characters.

Perl 5 solution

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

say swap_chars('perlandraku', 3, 4);

sub swap_chars {
	my ($S, $C, $O) = @_;
	my @s = split('', $S);
	my $N = scalar(@s) - 1;

	for (my $i = 1; $i <= $C; $i++) {
		my $temp           = $s[$i % $N];
		$s[$i % $N]        = $s[($i + $O) % $N];
		$s[($i + $O) % $N] = $temp;
	}

	return join '', @s;
}

Output: perl ./ch-1.pl 1 10000

pndraerlaku

Raku solution

# Test: perl6 ch-1.p6
sub MAIN() {
	say swap-chars('perlandraku', 3, 4);
}

sub swap-chars( Str $S, Int $C, Int $O) {
	my $N = $S.chars;
	my @s = $S.split('', :skip-empty);

	loop (my $i = 1; $i <= $C; $i++) {
		my $temp           = @s[$i % $N];
		@s[$i % $N]        = @s[($i + $O) % $N];
		@s[($i + $O) % $N] = $temp;
	}

	return @s.join('');
}

Output perl6 ch-1.p6

pndraerlaku

TASK #2 › Gray Code Sequence

Submitted by: Mohammad S Anwar

You are given an integer 2 <= $N <= 5.

Write a script to generate $N-bit gray code sequence.

2-bit Gray Code Sequence

[0, 1, 3, 2]

To generate the 3-bit Gray code sequence from the 2-bit Gray code sequence, follow the step below:

2-bit Gray Code sequence
[0, 1, 3, 2]

Binary form of the sequence
a) S1 = [00, 01, 11, 10]

Reverse of S1
b) S2 = [10, 11, 01, 00]

Prefix all entries of S1 with '0'
c) S1 = [000, 001, 011, 010]

Prefix all entries of S2 with '1'
d) S2 = [110, 111, 101, 100]

Concatenate S1 and S2 gives 3-bit Gray Code sequence
e) [000, 001, 011, 010, 110, 111, 101, 100]

3-bit Gray Code sequence
[0, 1, 3, 2, 6, 7, 5, 4]

Example

Input: $N = 4

Output: [0, 1, 3, 2, 6, 7, 5, 4, 12, 13, 15, 14, 10, 11, 9, 8]

This one just involved some string manipulation and converting the bit string to an integer.


Perl 5 solution

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

say gray_code(4);

sub gray_code {
	my $N = shift;
	my @S1 = ('00','01','11','10');

	while ($N > 2) {
		# Flip the array
		my @S2 = reverse @S1;

		# Prefix
		@S1 = map { '0' . $_ } @S1;
		@S2 = map { '1' . $_ } @S2;

		# Concatenate
		push @S1, @S2;

		$N--;
	}

	# Convert to decimal
	@S1 = map { oct("0b" . $_) } @S1;

	return '[' . (join ', ', @S1) . ']';
}

Output ./ch-2.pl

[0, 1, 3, 2, 6, 7, 5, 4, 12, 13, 15, 14, 10, 11, 9, 8]

Raku solution

# Test: perl6 ch-2.p6
sub MAIN() {
	say gray-code(4);
}

sub gray-code(Int $N is copy where $N >= 2 && $N <=5 ) {
	my @S1 = ('00','01','11','10');

	while ($N > 2) {
		# Flip the array
		my @S2 = @S1.reverse;

		# Prefix
		@S1 = @S1.map({ '0' ~ $_ });
		@S2 = @S2.map({ '1' ~ $_ });

		# Concatenate
		@S1 = flat @S1, @S2;

		$N--;
	}

	# Convert to decimal
	@S1 = @S1.map({ "0b$_".Int });

	return @S1.perl;
}

Output perl6 ch-2.p6

[0, 1, 3, 2, 6, 7, 5, 4, 12, 13, 15, 14, 10, 11, 9, 8]

One thought on “PERL WEEKLY CHALLENGE – 070

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