Task 1: Reverse Base
Given a number string and a base (2 <= base <= 36), reverse the digits of the number string and compute its decimal value.
Example Output
Input: $str = "123", $base = 10
Output: 321
Input: $str = "101", $base = 2
Output: 5
Logic
Reverse the character string, parse each digit in the specified radix/base, and evaluate the resulting integer in base 10.
Perl Solution
ch-1.pl
sub reverse_base ( $str, $base ) {
my $rev = reverse $str;
my @digits = ( '0' .. '9', 'a' .. 'z' );
my %val = map { $digits[$_] => $_ } 0 .. $#digits;
my $result = 0;
for my $char ( split //, lc($rev) ) {
die "Invalid digit '$char' for base $base" unless exists $val{$char} && $val{$char} < $base;
$result = $result * $base + $val{$char};
}
return $result;
}
Python Solution
ch-1.py
def reverse_base(num_str: str, base: int) -> int:
"""Reverse digits of num_str and evaluate in base."""
rev_str = num_str[::-1]
return int(rev_str, base)
Task 2: Rational Numbers
Compare two rational number representations including non-repeating and repeating decimal parts (e.g. 0.1(23)), return 1 if mathematically equal, 0 otherwise.
Example Output
Input: $rat1 = "0.1(23)", $rat2 = "0.12(32)"
Output: 1
Input: $rat1 = "12.99(99)", $rat2 = "13."
Output: 1
Logic
Parse the integer part, non-repeating fractional digits, and repeating digits into exact fractions using Math::BigRat in Perl and fractions.Fraction in Python, and test exact mathematical equality.
Perl Solution
ch-2.pl
sub parse_rational ($str) {
if ( $str =~ /^(\d+)(?:\.(\d*)(?:\((\d+)\))?)?$/ ) {
my $int_part = $1;
my $non_rep_part = $2 // '';
my $rep_part = $3 // '';
my $val = Math::BigRat->new($int_part);
if ( length($non_rep_part) > 0 || length($rep_part) > 0 ) {
if ( length($rep_part) == 0 ) {
$val += Math::BigRat->new( $non_rep_part . '/' . ( 10**length($non_rep_part) ) );
}
else {
my $len_non = length($non_rep_part);
my $len_rep = length($rep_part);
my $num = ( $non_rep_part . $rep_part ) - ( $non_rep_part || 0 );
my $den = ( ( 10**$len_rep ) - 1 ) * ( 10**$len_non );
$val += Math::BigRat->new("$num/$den");
}
}
return $val;
}
}
Python Solution
ch-2.py
def parse_rational(rat_str: str) -> Fraction:
"""Parse rational string like '0.1(23)' to Fraction."""
match = re.match(r"^(\d+)(?:\.(\d*)(?:\((\d+)\))?)?$", rat_str)
if not match:
raise ValueError(f"Invalid format: {rat_str}")
int_part, non_rep, rep = match.groups()
res = Fraction(int(int_part), 1)
non_rep = non_rep or ""
if not rep:
if non_rep:
res += Fraction(int(non_rep), 10 ** len(non_rep))
else:
len_non = len(non_rep)
len_rep = len(rep)
all_digits = int(non_rep + rep)
prefix_digits = int(non_rep) if non_rep else 0
num = all_digits - prefix_digits
den = (10**len_rep - 1) * (10**len_non)
res += Fraction(num, den)
return res