Zeckendorf arithmetic: Difference between revisions

m
(Added Go)
Line 603:
=={{header|Elena}}==
{{trans|C++}}
ELENA 3.24 :
<lang elena>import extensions.
 
const dig = ("00","01","10").
const dig1 = ("","1","10").
 
sealed struct ZeckendorfNumber :: BaseNumber
{
int dVal.
int dLen.
clone
= ZeckendorfNumber $newnewInternal(dVal,dLen).
stacksafe explicitcast n(LiteralValueliteral s)
[
int i := s length - 1.
int q := 1.
dLen := i / 2.
dVal := 0.
while (i >= 0)
[
dVal += ((intConvertor convert(s[i]) - 48) * q).
q *= 2.
i -= 1.
].
]
stacksafeinternal $readContent(ref<int> vint:val, ref<int> vint:len)
[
val intvalue := dVal.
len intvalue := dLen.
]
sealed $private a(IntNumberint n)
[
int i := n.
 
while (true)
[
Line 650:
dLen := i.
].
((dVal >> (i * 2)) && 3) =>
0 [ ^ $self ];
1 [ ^ $self ];
2 [
ifnot ((dVal >> ((i + 1) * 2)) allMask:1)
[
^ $self.
].
dVal += (1 << (i*2 + 1)).
^ $self.
];
3 [
dVal := dVal && ((3 << i*2) inverted).
$self $b((i+1)*2).
].
i += 1.
].
]
inc
[
dVal += 1.
$self $a(0).
]
$private b(IntNumberint pos)
[
if (pos == 0) [ ^ $self inc ].
ifnot((dVal >> pos) allMask:1)
[
dVal += (1 << pos).
$self $a(pos / 2).
if (pos > 1) [ $self $a((pos / 2) - 1) ]
];
[
dVal := dVal && (1 << pos) inverted.
$self $b(pos + 1).
$self $b(pos - (pos > 1) iif(2,1)).
].
]
 
$private c(IntNumber pos)
[
if ((dVal >> pos) allMask:1)
[
dVal := dVal && (1 << pos) inverted.
^ $self
].
$self $c(pos + 1).
if (pos > 0)
[
$self $b(pos - 1).
];
[
$self inc.
]
]
internal constructor $sum(ZeckendorfNumber n, ZeckendorfNumber m)
[
int mVal := 0.
int mLen := 0.
n $readContent vint:(&dVal, vint:&dLen).
m $readContent vint:(&mVal, vint:&mLen).
0 till((mLen + 1) * 2) do(:GN)
[
if (mVal shiftRight:GN; allMask:1)
[
$self $b(GN).
].
].
]
internal constructor $difference(ZeckendorfNumber n, ZeckendorfNumber m)
[
int mVal := 0.
int mLen := 0.
n $readContent vint:(&dVal, vint:&dLen).
m $readContent vint:(&mVal, vint:&mLen).
0 till((mLen + 1) * 2) do(:GN)
[
if (mVal shiftRight:GN; allMask:1)
[
$self $c(GN).
].
].
while ((((dVal >> (dLen*2)) && 3) == 0) || (dLen == 0))
[
Line 754:
].
]
internal constructor $product(ZeckendorfNumber n, ZeckendorfNumber m)
[
n $readContent vint:(&dVal, vint:&dLen).
var Na := m.
var Nb := m.
var Nr := 0n.
var Nt := 0n.
0 to((dLen + 1) * 2) do(:i)
[
Line 774:
Na := Nt.
].
Nr $readContent vint:(&dVal, vint:&dLen).
]
internal constructor $newnewInternal(IntNumberint v, IntNumberint l)
[
dVal := v.
dLen := l.
]
T<literal> literal
[
if (dVal == 0)
[ ^ "0". ].
literal s := dig1[(dVal >> (dLen * 2)) && 3].
int i := dLen - 1.
Line 794:
[
s := s + dig[(dVal >> (i * 2)) && 3].
i-=1
].
^ s.
]
add(ZeckendorfNumber n)
= ZeckendorfNumber $sum($self, n).
subtract(ZeckendorfNumber n)
= ZeckendorfNumber $difference($self, n).
multiply(ZeckendorfNumber n)
= ZeckendorfNumber $product($self, n).
}
 
programpublic =program
[
console printLine("Addition:").
var n := 10n.
n += 10n.
console printLine(n).
Line 826:
n += 10101n.
console printLine(n).
console printLine("Subtraction:").
n := 1000n.
Line 834:
n -= 1010101n.
console printLine(n).
console printLine("Multiplication:").
n := 1001n.
Line 842:
n += 101n.
console printLine(n).
].</lang>
{{out}}
<pre>
Anonymous user