P-Adic numbers, basic: Difference between revisions

m (→‎{{header|Raku}}: some updates)
Line 1,602:
<lang perl6># 20210225 Raku programming solution
 
#!/usr/bin/env raku
class Padic { has ($.p is default(2), @.v is default([])) is rw ;
 
class Padic { has ($.p is default(2), @%.v is default([]{})) is rw ;
 
method r2pa (Rat $x is copy, \p, \d) { # Reference: math.stackexchange.com/a/1187037
self.p = p ;
$x += p**d if $x < 0 ; # complement
 
my $lowerest = 0;
my ($num,$den) = $x.nude;
while ($den % p) == 0 { $den /= p and $lowerest-- }
$x = $num / $den;
 
while +self.v < d {
my %d = ^p Z=> (( $x «-« ^p ) »/» p )».&{ .denominator % p }; # .kv
for %d.keys { self.v.unshift:{$lowerest++} = $_ and last if %d{$_} != 0 }
$x = ($x - self.v.first{$lowerest-1}) / p ;
}
self
}
 
method add (Padic \x, \pd) {
my $div = 0;
my $lowerest = (self.v.keys.sort({.Int}).first,
x.v.keys.sort({.Int}).first ).min ;
return Padic.new:
p => self.p,
v => reverse gather for ( self.v.reverse Z x.v.reverse^d )».sum{
my $power = $lowerest + { given ($_+$div).polymod(p) { take .[0] ; $div = .[1] } }
given ((self.v.{$power}//0)+(x.v.{$power}//0)+$div).polymod(x.p)
{ take ($power, .[0]).Slip and $div = .[1] }
}
}
 
method gist { # en.wikipedia.org/wiki/P-adic_number#Notation
# en.wikipedia.org/wiki/P-adic_number#Notation
my %H = (0..9) Z=> ('₀'..'₉'); # (0x2080 .. 0x2089);
'⋯# 'my ~%H = self(0.v.9) ~Z=> (' '..'₉'); ~# [~](0x2080 self.p.comb».&{ %H{$_} } 0x2089);
# '⋯ ' ~ self.v ~ ' ' ~ [~] self.p.comb».&{ %H{$_} }
}
# express as a series
my %H = ( 0…9 ,'-') Z=> ( '⁰','¹','²','³','⁴'…'⁹','⁻');
[~] self.v.keys.sort({.Int}).map: {
' + ' ~ self.v.{$_} ~ '*' ~ self.p ~ [~] $_.comb».&{ %H{$_}} }
}
}
 
my @T;
for my \D = (
#`[[[[[ these are not working
< -726/525 99-109/70125 75 4> >,
< 26/25 -109/125 5 5 >,
< 5/19 -101/384 2 12>,
< 6/7 -5/7 10 7 >,
< 2/7 -3/7 10 7 >,
< 2/7 -1/7 10 7 >,
< 34/21 -39034/791 10 9 >,
# ]]]]]
#`[[[[[ Works
< 11/4 679001/207 2 43>,
< 11/4 679001/207 3 27 >,
< 265/2519 -109101/125384 5 52 12>,
< -22/7 46071/379 7 13 >,
< 5-7/195 -10199/38470 27 124> ,
< -101/109 583376/6649 61 7>,
< 122/407 -517/1477 7 11>,
 
# ]]]]]
#`[[[[[ working cases
< 2/1 1/1 2 4>,
< 4/1 3/1 2 4>,
Line 1,656 ⟶ 1,676:
< -22/7 46071/379 2 37 >,
< -22/7 46071/379 3 23 >,
 
< -101/109 583376/6649 2 40>,
< -101/109 583376/6649 32749 3>,
< -25/26 5571/137 7 13>,
# ]]]]]
 
< 5/8 353/30809 7 11 >,
Line 1,665 ⟶ 1,686:
given @T[0] = Padic.new { say D[0]~' = ', .r2pa: D[0],D[2],D[3] }
given @T[1] = Padic.new { say D[1]~' = ', .r2pa: D[1],D[2],D[3] }
given @T[0].add: @T[1], D[23] {
given @T[2] = Padic.new { .r2pa: D[0]+D[1], D[2], D[3] }
say "Addition result = ", $_.gist, ( $_.gist eqv @T[2].gist ) ?? ''; #
unless ( !! ' but ' ~ (D[0]+D[1])$_.nudev.join('/')Str ~ ' = ' ~eq @T[2].gistv.Str ) {
say 'but ' ~ (D[0]+D[1]).nude.join('/') ~ ' = ' ~ @T[2].gist
}
}
}
</lang>
{{out}}
<pre>
<pre>5/8 = ⋯ 4 2 4 2 4 2 4 2 4 2 5 ₇
5/8 = + 5*7⁰ + 2*7¹ + 4*7² + 2*7³ + 4*7⁴ + 2*7⁵ + 4*7⁶ + 2*7⁷ + 4*7⁸ + 2*7⁹ + 4*7¹⁰
353/30809 = ⋯ 2 3 6 6 3 6 4 3 4 5 5 ₇
353/30809 = + 5*7⁰ + 5*7¹ + 4*7² + 3*7³ + 4*7⁴ + 6*7⁵ + 3*7⁶ + 6*7⁷ + 6*7⁸ + 3*7⁹ + 2*7¹⁰
Addition result = ⋯ 6 6 4 2 1 2 1 6 2 1 3 ₇
Addition result = + 3*7⁰ + 1*7¹ + 2*7² + 6*7³ + 1*7⁴ + 2*7⁵ + 1*7⁶ + 2*7⁷ + 4*7⁸ + 6*7⁹ + 6*7¹⁰
</pre>
 
350

edits