diff options
| -rw-r--r-- | challenge-281/mgo1977/perl/ch-1.pl | 66 | ||||
| -rw-r--r-- | challenge-281/mgo1977/perl/ch-2.pl | 223 |
2 files changed, 289 insertions, 0 deletions
diff --git a/challenge-281/mgo1977/perl/ch-1.pl b/challenge-281/mgo1977/perl/ch-1.pl new file mode 100644 index 0000000000..8079a06c6d --- /dev/null +++ b/challenge-281/mgo1977/perl/ch-1.pl @@ -0,0 +1,66 @@ +#!/bin/perl -w + + +use Data::Dump qw(dump); + + +# Task 1: Check Color +# Submitted by: Mohammad Sajid Anwar +# You are given coordinates, a string that represents the coordinates of a square of the chessboard as shown below: + +# Week_281_Task_1 + +# Write a script to return true if the square is light, and false if the square is dark. + +# Example 1 +# Input: $coordinates = "d3" +# Output: true +# Example 2 +# Input: $coordinates = "g5" +# Output: false +# Example 3 +# Input: $coordinates = "e6" +# Output: true + + + +testMe(\&process, 'Example1', "d3", 1); +testMe(\&process, 'Example2', "g5", 0); +testMe(\&process, 'Example3', "e6", 1); + +sub testMe { + my $processor = shift; + my $name = shift; + my $input1 = shift; + my $expectedValue = shift; + + my $got = &$processor($input1); + + if ( $got == $expectedValue ) { + print "[OK ] $name\n"; + } + else { + print "[ERR] $name :: got='$got', expectedValue='$expectedValue'\n"; + } + +} + + +sub process { + my $input1 = shift; + + if ( $input1 !~ /([a-h])([1-8])/i ) { + return 0; + } + + my ($a,$b) = ( charToInt($1), int($2)); + + return ($a+$b)%2!=0; + +} + +sub charToInt { + my $v = uc(shift); + + return ord($v) - ord('A') + 1; +}
\ No newline at end of file diff --git a/challenge-281/mgo1977/perl/ch-2.pl b/challenge-281/mgo1977/perl/ch-2.pl new file mode 100644 index 0000000000..3e5ac2167d --- /dev/null +++ b/challenge-281/mgo1977/perl/ch-2.pl @@ -0,0 +1,223 @@ +#!/bin/perl -w + + +# Task 2: Knightâs Move +# Submitted by: Peter Campbell Smith +# A Knight in chess can move from its current position to any square two rows or columns plus one column or row away. So in the diagram below, if it starts a S, it can move to any of the squares marked E. + +# Write a script which takes a starting position and an ending position and calculates the least number of moves required. + +# Week_281_Task_2 + +# Example 1 +# Input: $start = 'g2', $end = 'a8' +# Ouput: 4 + +# g2 -> e3 -> d5 -> c7 -> a8 +# Example 2 +# Input: $start = 'g2', $end = 'h2' +# Ouput: 3 + +# g2 -> e3 -> f1 -> h2 + + +testMe(\&process, 'Example1', "g2", "a8", 4); +testMe(\&process, 'Example2', "g2", "h2", 3); +testMe(\&process, 'Example3', "g2", "g2", 0); +testMe(\&process, 'Example4', "g2", "f4", 1); + +sub testMe { + my $processor = shift; + my $name = shift; + my $input1 = shift; + my $input2 = shift; + my $expectedValue = shift; + + my $got = &$processor($input1, $input2); + + if ( $got == $expectedValue ) { + print "[OK ] $name\n"; + } + else { + print "[ERR] $name :: got=$got, expectedValue=$expectedValue\n"; + } + +} + +sub process { + my $start = shift; + my $end = shift; + + + my $startPos = parse($start); + my $endPos = parse($end); + + # print("start=$start (@$startPos) end=$end (@$endPos)\n"); + + my $context = { + alreadyVisited => { toText($startPos) => 1}, + shortestSolution => undef, + }; + + + doMove(0, $context, undef, $startPos, $endPos); + + # print "process called with startPos=" . toText($startPos) . " and endPos=" . toText($endPos) . + # ", shortestSolution=" . toTextList($context->{'shortestSolution'}) . + # "\n"; + + if ( not defined $context->{'shortestSolution'} ) { + return -1; + } + + return scalar @{$context->{'shortestSolution'}}; + +} + + +sub doMove { + my $index = shift; + my $context = shift; + my $currentSolution = shift || []; + my $currentPos = shift; + my $endPos = shift; + + if ( defined $context->{'shortestSolution'} ) { + + my $bestLen = scalar @{$context->{'shortestSolution'}}; + my $thisSolutionLen = scalar @$currentSolution; + + if ( $thisSolutionLen >= $bestLen ) { + # stop processing as early as possible + return; + } + } + + # print "#$index - doMove called with currentPos=" . toText($currentPos) . " and endPos=" . toText($endPos) . + # ", currentSolution=" . toTextList($currentSolution) . + # ", alreadyVisited=" . join(',', keys(%{$context->{'alreadyVisited'}})) . + # "\n"; + + if ( areEquals($currentPos, $endPos) ) { + $context->{'shortestSolution'} = [ @$currentSolution ]; + return; + } + + + my $validMoves = findValidMoves($currentPos); + #print "from " . toText($currentPos) . " valid moves are: " . toTextList($validMoves) . "\n"; + + foreach my $validMove ( @$validMoves ) { + + my $thisMoveText = toText($validMove); + + if ( exists $context->{'alreadyVisited'}->{$thisMoveText} ) { + # already visited... + next; + } + else { + $context->{'alreadyVisited'}->{$thisMoveText} = 1; + push(@$currentSolution, $validMove); + + doMove($index+1, $context, $currentSolution, $validMove, $endPos); + + pop(@$currentSolution); + delete $context->{'alreadyVisited'}->{$thisMoveText}; + + } + + } +} + + +sub findValidMoves { + my $pos = shift; + + #print "findValidMoves called from pos=" . toText($pos) . "\n"; + + my @validList; + + my $addIfValid = sub { + my $a = shift; + + if ( + $a->[0]<1 || $a->[0]>8 || + $a->[1]<1 || $a->[1]>8 + ) { + return; + } + + push(@validList, $a); + }; + + $addIfValid->([$pos->[0]+2, $pos->[1]-1]); + $addIfValid->([$pos->[0]+2, $pos->[1]+1]); + $addIfValid->([$pos->[0]-2, $pos->[1]-1]); + $addIfValid->([$pos->[0]-2, $pos->[1]+1]); + + $addIfValid->([$pos->[0]+1, $pos->[1]-2]); + $addIfValid->([$pos->[0]+1, $pos->[1]+2]); + $addIfValid->([$pos->[0]-1, $pos->[1]-2]); + $addIfValid->([$pos->[0]-1, $pos->[1]+2]); + + return \@validList; +} + + +sub toText { + my $a = shift; + + if ( not defined $a ) { + return '<undef>'; + } + + return intToChar($a->[0]) . $a->[1]; +} + +sub toTextList { + my $list = shift; + + if ( not defined $list ) { + return '<undef>'; + } + + return '[' . join(',', map { toText($_) } @$list ) . ']'; +} + + +sub areEquals { + my ($a, $b) = @_; + + return $a->[0]==$b->[0] && $a->[1]==$b->[1]; +} + +sub parse { + my $textNotation = shift; + + if ( $textNotation !~ /([a-h])([1-8])/i ) { + die "Unexpected textNotation=$textNotation"; + } + + my ($a,$b) = ( charToInt($1), int($2)); + + return [ $a, $b ]; + +} + +sub charToInt { + my $v = shift; + + if ( not defined $v ) { + return '<undef>'; + } + + #print "got v=$v\n"; + + return ord( uc($v) ) - ord('A') + 1; +} + +sub intToChar { + my $v = shift; + + return chr( ord('a') + $v - 1 ); +}
\ No newline at end of file |
