Negative base numbers: Difference between revisions

added RPL
(Added 11l)
(added RPL)
(15 intermediate revisions by 10 users not shown)
Line 19:
{{trans|Python}}
 
<langsyntaxhighlight lang="11l">F encode_neg_base(=n, b)
I n == 0
R ‘0’
Line 60:
print(‘Converted back to decimal’)
E
print(‘Error converting back to decimal’)</langsyntaxhighlight>
 
{{out}}
Line 74:
Converted back to decimal
</pre>
 
=={{header|Action!}}==
<syntaxhighlight lang="action!">CHAR ARRAY digits="0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz!"
 
INT FUNC MyMod(INT a,b)
IF b>=0 THEN
RETURN (a MOD b)
FI
RETURN (a-(b*(a/b)))
 
PROC Encode(INT n,base CHAR ARRAY res)
INT i,d,len
CHAR tmp
 
IF base<-63 OR base>-1 THEN Break() FI
IF n=0 THEN SAssign(res,"0") FI
 
len=0
WHILE n#0
DO
d=MyMod(n,base)
n==/base
IF d<0 THEN
n==+1
d==-base
FI
len==+1
res(len)=digits(d+1)
OD
res(0)=len
 
FOR i=1 to len/2
DO
tmp=res(i)
res(i)=res(len-i+1)
res(len-i+1)=tmp
OD
RETURN
 
BYTE FUNC Index(CHAR ARRAY s CHAR c)
BYTE i
 
FOR i=1 TO s(0)
DO
IF s(i)=c THEN RETURN (i) FI
OD
RETURN (0)
 
INT FUNC Decode(CHAR ARRAY s INT base)
INT res,b,i,pos
 
IF base<-63 OR base>-1 THEN Break() FI
IF s(0)=1 AND s(1)='0 THEN RETURN (0) FI
 
res=0
b=1
pos=s(0)
WHILE pos>=1
DO
i=Index(digits,s(pos))-1
res==+i*b
b==*base
pos==-1
OD
RETURN (res)
 
PROC Test(INT n,base)
CHAR ARRAY s(20)
INT v
 
Encode(n,base,s)
PrintF("%I encoded in base %I is %S%E",n,base,s)
v=Decode(s,base)
PrintF("%S decoded in base %I is %I%E%E",s,base,v)
RETURN
 
PROC Main()
INT v
Test(10,-2)
Test(146,-3)
Test(15,-10)
Test(-568,-63)
RETURN</syntaxhighlight>
{{out}}
[https://gitlab.com/amarok8bit/action-rosetta-code/-/raw/master/images/Negative_base_numbers.png Screenshot from Atari 8-bit computer]
<pre>
10 encoded in base -2 is 11110
11110 decoded in base -2 is 10
 
146 encoded in base -3 is 21102
21102 decoded in base -3 is 146
 
15 encoded in base -10 is 195
195 decoded in base -10 is 15
 
-568 encoded in base -63 is A!
A! decoded in base -63 is -568
</pre>
 
=={{header|Ada}}==
{{trans|Modula}}
 
<syntaxhighlight lang="ada">with Ada.Strings.Unbounded; use Ada.Strings.Unbounded;
 
package Negative_Base_Numbers is
 
subtype base_t is Long_Long_Integer range -62 .. -1;
 
function Encode_Negative_Base
(N : in Long_Long_Integer; Base : in base_t) return Unbounded_String;
function Decode_Negative_Base
(N : in Unbounded_String; Base : in base_t) return Long_Long_Integer;
 
end Negative_Base_Numbers;
 
with Ada.Text_IO;
package body Negative_Base_Numbers is
 
Digit_Chars : constant String :=
"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
 
--------------------------
-- Encode_Negative_Base --
--------------------------
 
function Encode_Negative_Base
(N : in Long_Long_Integer; Base : in base_t) return Unbounded_String
is
procedure swap (a, b : in out Character) is
temp : Character := a;
begin
a := b;
b := temp;
end swap;
 
Result : Unbounded_String := Null_Unbounded_String;
Local_N : Long_Long_Integer := N;
Remainder : Long_Long_Integer;
 
begin
if Local_N = 0 then
Result := To_Unbounded_String ("0");
else
while Local_N /= 0 loop
Remainder := Local_N rem Base;
Local_N := Local_N / Base;
if Remainder < 0 then
Local_N := Local_N + 1;
Remainder := Remainder - Base;
end if;
Append (Result, Digit_Chars (Integer (Remainder + 1)));
end loop;
end if;
 
declare
Temp_Result : String := To_String (Result);
Low : Positive := Temp_Result'First;
High : Positive := Temp_Result'Last;
begin
while Low < High loop
swap (Temp_Result (Low), Temp_Result (High));
Low := Low + 1;
High := High - 1;
end loop;
Result := To_Unbounded_String (Temp_Result);
end;
 
return Result;
end Encode_Negative_Base;
 
--------------------------
-- Decode_Negative_Base --
--------------------------
 
function Decode_Negative_Base
(N : in Unbounded_String; Base : in base_t) return Long_Long_Integer
is
Total : Long_Long_Integer := 0;
bb : Long_Long_Integer := 1;
Temp : String := To_String (N);
begin
if Length (N) = 0 or else (Length (N) = 1 and Element (N, 1) = '0') then
return 0;
end if;
 
for char of reverse Temp loop
for J in Digit_Chars'Range loop
if char = Digit_Chars (J) then
Total := Total + Long_Long_Integer (J - 1) * bb;
bb := bb * Base;
end if;
end loop;
end loop;
 
return Total;
end Decode_Negative_Base;
 
end Negative_Base_Numbers;
 
with Ada.Text_IO; use Ada.Text_IO;
with Negative_Base_Numbers; use Negative_Base_Numbers;
with Ada.Strings.Fixed; use Ada.Strings.Fixed;
with Ada.Strings.Unbounded; use Ada.Strings.Unbounded;
 
procedure Main is
 
procedure driver (N : in Long_Long_Integer; B : in base_t) is
package long_IO is new Integer_IO (Long_Long_Integer);
use long_IO;
 
ns : Unbounded_String := Encode_Negative_Base (N, B);
P : Long_Long_Integer;
Output : String (1 .. 12);
 
begin
Put (Item => N, Width => 12);
Put (" encoded in base ");
Put (Item => B, Width => 3);
Put_Line (" = " & To_String (ns));
 
Move
(Source => To_String (ns), Target => Output,
Justify => Ada.Strings.Right);
P := Decode_Negative_Base (ns, B);
Put (Output & " decoded in base ");
Put (Item => B, Width => 3);
Put (" = ");
Put (Item => P, Width => 1);
New_Line (2);
end driver;
 
begin
driver (10, -2);
driver (146, -3);
driver (15, -10);
driver (36_058, -62);
end Main;</syntaxhighlight>
{{out}}
<pre>
10 encoded in base -2 = 11110
11110 decoded in base -2 = 10
 
146 encoded in base -3 = 21102
21102 decoded in base -3 = 146
 
15 encoded in base -10 = 195
195 decoded in base -10 = 15
 
36058 encoded in base -62 = Ada
Ada decoded in base -62 = 36058</pre>
 
=={{header|ALGOL 68}}==
{{works with|ALGOL 68G|Any - tested with release 2.8.3.win32}}
<langsyntaxhighlight lang="algol68"># Conversion to/from negative base numbers #
# Note - no checks for valid bases or digits bases -2 .. -63 are handled #
# A-Z represent the digits 11 .. 35, a-z represent the digits 36 .. 61 #
Line 145 ⟶ 395:
# The defining document for ALGOL 68 spells the name "Algol 68" on the cover, though inside it is "ALGOL 68" #
# at the risk of "judging a language by it's cover", we use "Algol 68" as the name here... #
test n base( - LONG 36492107981104, -63, "Algol 68" )</langsyntaxhighlight>
{{out}}
<pre>
Line 160 ⟶ 410:
=={{header|C}}==
{{trans|modula-2}}
<langsyntaxhighlight lang="c">#include <stdio.h>
 
const char DIGITS[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
Line 262 ⟶ 512:
 
return 0;
}</langsyntaxhighlight>
{{out}}
<pre> 10 encoded in base -2 = 11110
Line 278 ⟶ 528:
=={{header|C sharp|C#}}==
{{trans|Java}}
<langsyntaxhighlight lang="csharp">using System;
using System.Collections.Generic;
using System.Linq;
Line 341 ⟶ 591:
}
}
}</langsyntaxhighlight>
{{out}}
<pre> 10 encoded in base -2 = 11110
Line 357 ⟶ 607:
=={{header|C++}}==
{{trans|C#}}
<langsyntaxhighlight lang="cpp">#include <iomanip>
#include <iostream>
#include <tuple>
Line 431 ⟶ 681:
 
return 0;
}</langsyntaxhighlight>
{{out}}
<pre> 10 encoded in base -2 = 11110
Line 446 ⟶ 696:
 
=={{header|D}}==
<langsyntaxhighlight Dlang="d">import std.stdio;
 
immutable DIGITS = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
Line 507 ⟶ 757:
}
return total;
}</langsyntaxhighlight>
 
{{out}}
Line 524 ⟶ 774:
=={{header|F_Sharp|F#}}==
===The Functions===
<langsyntaxhighlight lang="fsharp">
//I provide 2 fuctions D2N takes a radix and an integer returning a sequence of integers
// N2D takse a radix and a sequence of integers returning an integer
Line 533 ⟶ 783:
|_->Some(g-(α+1)*n,α+1)) g|>Seq.rev
let N2D n g=fst(Seq.foldBack(fun g (Σ,α)->(Σ+α*g,n*α)) g (0,1))
</syntaxhighlight>
</lang>
===The Task===
<langsyntaxhighlight lang="fsharp">
let t0,t146,t10,t15=D2N -13 0,D2N -3 146,D2N -2 10,D2N -10 15
Seq.iter(fun n->Seq.iter(printf "%d ")n; printfn "")[t0;t146;t10;t15]
Seq.iter(printfn "%d ")[N2D -13 t0;N2D -3 t146;N2D -2 t10;N2D -10 t15]
</syntaxhighlight>
</lang>
{{out}}
<pre>
Line 554 ⟶ 804:
=={{header|Factor}}==
{{works with|Factor|0.99 2020-03-02}}
<langsyntaxhighlight lang="factor">USING: formatting fry kernel make math math.combinators
math.extras math.functions math.parser sequences ;
 
Line 570 ⟶ 820:
"%d_10 is %s_%d\n%s_%d is %d_10\n\n" printf ;
 
10 -2 146 -3 15 -10 [ .round-trip ] 2tri@</langsyntaxhighlight>
{{out}}
<pre>
Line 582 ⟶ 832:
195_-10 is 15_10
</pre>
 
=={{header|FreeBASIC}}==
{{trans|VBA}}
<syntaxhighlight lang="vb">#define DIGITS "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
 
Dim cadena(63) As String
 
Function mod2(a As Long, b As Integer) As Long
Return a - (a \ b) * b
End Function
 
Function StrReverse(Byval text As String) As String
Dim As String text2 = text
Dim As Integer x, lt = Len(text)
For x = 0 To lt Shr 1 - 1
Swap text2[x], text2[lt - x - 1]
Next x
Return text2
End Function
 
Function EncodeNegativeBase(Byval n As Long, base_ As Integer) As String
Dim As Long Puntero, idx, rem_
Dim result As String
If base_ > -1 Or base_ < -62 Then
Return result
Else
If n = 0 Then
Return "0"
Else
Puntero = 0
Do While n <> 0
rem_ = mod2(n, base_)
n \= base_
If rem_ < 0 Then
n += 1
rem_ = rem_ - base_
End If
result &= Mid(DIGITS, rem_ + 1, 1)
Loop
End If
End If
Return StrReverse(result)
End Function
 
Function DecodeNegativeBase(ns As String, base_ As Integer) As Long
Dim As Long total, bb
Dim As Integer i, j
If base_ < -62 Or base_ > -1 Then Return 0
If Mid(ns, 1, 1) = "0" Or (Mid(ns, 1, 1) = "0" And Mid(ns, 2, 1) = "0") Then Return 0
i = Len(ns)
total = 0
bb = 1
Do While i >= 1
j = Instr(DIGITS, Mid(ns, i, 1)) - 1
total += j * bb
bb *= base_
i -= 1
Loop
Return total
End Function
 
Sub Driver(n As Long, b As Integer)
Dim As String ns = EncodeNegativeBase(n, b)
Print Str(n); " encoded in base "; b; " = "; ns
Dim As Long p = DecodeNegativeBase(ns, b)
Print ns; " decoded in base "; b; " ="; p
Print
End Sub
 
Driver 10, -2
Driver 146, -3
Driver 15, -10
Driver 118492, -62
 
Sleep</syntaxhighlight>
{{out}}
<pre>Same as VBA entry.</pre>
 
=={{header|Go}}==
{{trans|Kotlin}}
<langsyntaxhighlight lang="go">package main
 
import (
Line 658 ⟶ 988:
fmt.Printf("%13s decoded in base %-3d = %d\n\n", ns, b, n)
}
}</langsyntaxhighlight>
 
{{out}}
Line 679 ⟶ 1,009:
 
=={{header|Haskell}}==
<langsyntaxhighlight lang="haskell">import Data.Char (chr, ord)
import Numeric (showIntAtBase)
 
Line 711 ⟶ 1,041:
printAtBase (-10) 15
printAtBase (-16) 107
printAtBase (-36) 41371458</langsyntaxhighlight>
 
{{out}}
Line 815 ⟶ 1,145:
{{trans|Kotlin}}
{{works with|Java|9}}
<langsyntaxhighlight Javalang="java">import java.util.List;
import java.util.Map;
import java.util.Objects;
Line 867 ⟶ 1,197:
}
}
}</langsyntaxhighlight>
{{out}}
<pre> 10 encoded in base -2 = 11110
Line 884 ⟶ 1,214:
{{works with|jq|1.5}}
If your jq does not have `trunc/0` then use this:
<langsyntaxhighlight lang="jq">def trunc: if . >= 0 then floor else -(-(.)|trunc) end;</langsyntaxhighlight>
<langsyntaxhighlight lang="jq">def negbase($b):
if ($b >= 0) then error("negbase requires negative base")
elif . == 0 then "0"
Line 918 ⟶ 1,248:
;
 
test</langsyntaxhighlight>
{{out}}
<langsyntaxhighlight lang="jq">[true,true]
[true,true]
[true,true]</langsyntaxhighlight>
 
=={{header|Julia}}==
{{works with|Julia|0.6}}
 
<langsyntaxhighlight lang="julia">
function negbase(n, b)
if n == 0 return "0" end
Line 953 ⟶ 1,283:
decoded = invnegbase(encoded, base)
println("\nencode $num in base $base:\n-> expected: $rst\n-> resulted: $encoded\n-> decoded: $decoded")
end</langsyntaxhighlight>
 
{{out}}
Line 972 ⟶ 1,302:
 
=={{header|Kotlin}}==
<langsyntaxhighlight lang="scala">// version 1.1.2
 
const val DIGITS = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
Line 1,014 ⟶ 1,344:
System.out.printf("%12s decoded in base %-3d = %d\n\n", ns, p.second, n)
}
}</langsyntaxhighlight>
 
{{out}}
Line 1,031 ⟶ 1,361:
</pre>
 
=={{header|Mathematica}}/{{header|Wolfram Language}}==
<langsyntaxhighlight Mathematicalang="mathematica">EncodeBase[number_,base_]:=Module[{
out={},
rem,n=number,b=base
Line 1,052 ⟶ 1,382:
Print[EncodeNegBase[10,-2],"=",DecodeBase[EncodeNegBase[10,-2],-2]];
Print[EncodeNegBase[146,-3],"=",DecodeBase[EncodeNegBase[146,-3],-3]];
Print[EncodeNegBase[15,-10],"=",DecodeBase[EncodeNegBase[15,-10],-10]];</langsyntaxhighlight>
<pre>{1,1,1,1,0}=10
{2,1,1,0,2}=146
{1,9,5}=15</pre>
Extra Credit:
<langsyntaxhighlight Mathematicalang="mathematica">DecodeBase[ToCharacterCode[$Version], -126](*ascii 1-byte encoding*)
DecodeBase[ToCharacterCode[$Version], -(2^16 - 1)](*2-byte encoding*)</langsyntaxhighlight>
<pre>805433247971592164648901981307140864173502418954511864100981464890629926293823767730118860531000284192172723837
1402171866107096793294662824351970913227448502019658754262020315290937172496459102043149157175108006798078612200544768242812932737034448604720533372980987964929785521161173764118702296122915325508945150191589743829011670147956776269027485433441427722106</pre>
 
=={{header|Modula-2}}==
<langsyntaxhighlight lang="modula2">MODULE NegativeBase;
FROM FormatString IMPORT FormatString;
FROM Terminal IMPORT WriteString,WriteLn,ReadChar;
Line 1,173 ⟶ 1,503:
 
ReadChar
END NegativeBase.</langsyntaxhighlight>
{{out}}
<pre> 10 encoded in base -2 = 11110
Line 1,186 ⟶ 1,516:
-19425187910 encoded in base -62 = Modula
Modula decoded in base -62 = -19425187910</pre>
 
=={{header|Nim}}==
<syntaxhighlight lang="nim">import algorithm, sugar, tables
 
const
Digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
Values = collect(initTable):
for i, c in Digits: {c: i} # Maps the digits to their values in base 10.
 
type Number = object
## Representation of a number in any base.
base: int
value: string
 
func toBase(n, base: int): Number =
## Convert an integer into a number in base 'base'.
assert base notin -1..1, "wrong value for base: " & $base
if n == 0: return Number(base: base, value: "0")
result.base = base
var n = n
while n != 0:
var m = n mod base
n = n div base
if m < 0:
inc m, abs(base)
inc n
result.value.add Digits[m]
result.value.reverse()
 
func `$`(n: Number): string =
## String representation of a number.
$n.value
 
func toInt(n: Number): int =
## Convert a number in some base into an integer in base 10.
for d in n.value:
result = n.base * result + Values[d]
 
 
when isMainModule:
 
proc process(n, base: int) =
let s = n.toBase(base)
echo "The value ", n, " is encoded in base ", base, " as: ", s
echo "and is decoded back in base 10 as: ", s.toInt
echo ""
 
process(10, -2)
process(146, -3)
process(15, -10)
 
const Nim = Number(base: -62, value: "Nim")
echo "The string “Nim” is decoded from base -62 to base 10 as: ", Nim.toInt</syntaxhighlight>
 
{{out}}
<pre>The value 10 is encoded in base -2 as: 11110
and is decoded back in base 10 as: 10
 
The value 146 is encoded in base -3 as: 21102
and is decoded back in base 10 as: 146
 
The value 15 is encoded in base -10 as: 195
and is decoded back in base 10 as: 15
 
The string “Nim” is decoded from base -62 to base 10 as: 85732</pre>
 
=={{header|ooRexx}}==
{{trans|REXX}}
<langsyntaxhighlight lang="oorexx">/* REXX ---------------------------------------------------------------
* Adapt for ooRexx (use of now invalid variable names)
* and make it work for base -63 (Algol example)
Line 1,247 ⟶ 1,642:
Else
r='ok'
Return r</langsyntaxhighlight>
{{out}}
<pre> 10 converted to base -2 ----> 11110 ok
Line 1,259 ⟶ 1,654:
=={{header|Perl}}==
{{libheader|ntheory}}
<langsyntaxhighlight lang="perl">use strict;
use feature 'say';
use POSIX qw(floor);
Line 1,295 ⟶ 1,690:
say '11110 from base -2: ', decode("11110", -2);
say '21102 from base -3: ', decode("21102", -3);
say ' 195 from base -10: ', decode("195", -10);</langsyntaxhighlight>
{{out}}
<pre>
Line 1,307 ⟶ 1,702:
 
=={{header|Phix}}==
<!--<syntaxhighlight lang="phix">(phixonline)-->
<lang Phix>constant digits = "0123456789"&
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"&
<span style="color: #008080;">constant</span> <span style="color: #000000;">digits</span> <span style="color: #0000FF;">=</span> <span style="color: #008000;">"0123456789"</span><span style="color: #0000FF;">&</span>
"abcdefghijklmnopqrstuvwxyz"
<span style="color: #008000;">"ABCDEFGHIJKLMNOPQRSTUVWXYZ"</span><span style="color: #0000FF;">&</span>
 
<span style="color: #008000;">"abcdefghijklmnopqrstuvwxyz"</span>
type base(integer b)
return b<=-1 and b>=-length(digits)
<span style="color: #008080;">type</span> <span style="color: #000000;">base</span><span style="color: #0000FF;">(</span><span style="color: #004080;">integer</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
end type
<span style="color: #008080;">return</span> <span style="color: #000000;">b</span><span style="color: #0000FF;"><=-</span><span style="color: #000000;">1</span> <span style="color: #008080;">and</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">>=-</span><span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">digits</span><span style="color: #0000FF;">)</span>
 
<span style="color: #008080;">end</span> <span style="color: #008080;">type</span>
function encodeNegBase(atom n, base b)
string res = iff(n?"":"0")
<span style="color: #008080;">function</span> <span style="color: #000000;">encodeNegBase</span><span style="color: #0000FF;">(</span><span style="color: #004080;">atom</span> <span style="color: #000000;">n</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">base</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
while n!=0 do
<span style="color: #004080;">string</span> <span style="color: #000000;">res</span> <span style="color: #0000FF;">=</span> <span style="color: #008080;">iff</span><span style="color: #0000FF;">(</span><span style="color: #000000;">n</span><span style="color: #0000FF;">?</span><span style="color: #008000;">""</span><span style="color: #0000FF;">:</span><span style="color: #008000;">"0"</span><span style="color: #0000FF;">)</span>
atom r = remainder(n,b)
<span style="color: #008080;">while</span> <span style="color: #000000;">n</span><span style="color: #0000FF;">!=</span><span style="color: #000000;">0</span> <span style="color: #008080;">do</span>
n = trunc(n/b)
<span style="color: #004080;">atom</span> <span style="color: #000000;">r</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">remainder</span><span style="color: #0000FF;">(</span><span style="color: #000000;">n</span><span style="color: #0000FF;">,</span><span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
if r<0 then
<span style="color: #000000;">n</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">trunc</span><span style="color: #0000FF;">(</span><span style="color: #000000;">n</span><span style="color: #0000FF;">/</span><span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
n += 1
<span style="color: #008080;">if</span> <span style="color: #000000;">r</span><span style="color: #0000FF;"><</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
r -= b
<span style="color: #000000;">n</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
end if
<span style="color: #000000;">r</span> <span style="color: #0000FF;">-=</span> <span style="color: #000000;">b</span>
res &= digits[r+1]
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
end while
<span style="color: #000000;">res</span> <span style="color: #0000FF;">&=</span> <span style="color: #000000;">digits</span><span style="color: #0000FF;">[</span><span style="color: #000000;">r</span><span style="color: #0000FF;">+</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span>
return reverse(res)
<span style="color: #008080;">end</span> <span style="color: #008080;">while</span>
end function
<span style="color: #008080;">return</span> <span style="color: #7060A8;">reverse</span><span style="color: #0000FF;">(</span><span style="color: #000000;">res</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">decodeNegBase</span><span style="color: #0000FF;">(</span><span style="color: #004080;">string</span> <span style="color: #000000;">ns</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">base</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #004080;">atom</span> <span style="color: #000000;">total</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span><span style="color: #0000FF;">,</span>
<span style="color: #000000;">bb</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">1</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">ns</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">to</span> <span style="color: #000000;">1</span> <span style="color: #008080;">by</span> <span style="color: #0000FF;">-</span><span style="color: #000000;">1</span> <span style="color: #008080;">do</span>
<span style="color: #004080;">integer</span> <span style="color: #000000;">k</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">find</span><span style="color: #0000FF;">(</span><span style="color: #000000;">ns</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">],</span><span style="color: #000000;">digits</span><span style="color: #0000FF;">)-</span><span style="color: #000000;">1</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">k</span><span style="color: #0000FF;">=-</span><span style="color: #000000;">1</span> <span style="color: #008080;">or</span> <span style="color: #000000;">k</span><span style="color: #0000FF;">>-</span><span style="color: #000000;">b</span> <span style="color: #008080;">then</span> <span style="color: #008080;">return</span> <span style="color: #008000;">"invalid digit"</span> <span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #000000;">total</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">k</span><span style="color: #0000FF;">*</span><span style="color: #000000;">bb</span>
<span style="color: #000000;">bb</span> <span style="color: #0000FF;">*=</span> <span style="color: #000000;">b</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">total</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #000080;font-style:italic;">-- decimal, base, expected</span>
function decodeNegBase(string ns, base b)
<span style="color: #008080;">constant</span> <span style="color: #000000;">tests</span> <span style="color: #0000FF;">=</span> <span style="color: #0000FF;">{{</span><span style="color: #000000;">10</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">-</span><span style="color: #000000;">2</span><span style="color: #0000FF;">,</span> <span style="color: #008000;">"11110"</span><span style="color: #0000FF;">},</span>
atom total = 0,
<span style="color: #0000FF;">{</span><span style="color: #000000;">146</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">-</span><span style="color: #000000;">3</span><span style="color: #0000FF;">,</span> <span style="color: #008000;">"21102"</span><span style="color: #0000FF;">},</span>
bb = 1
<span style="color: #0000FF;">{</span><span style="color: #000000;">15</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">-</span><span style="color: #000000;">10</span><span style="color: #0000FF;">,</span> <span style="color: #008000;">"195"</span><span style="color: #0000FF;">},</span>
for i=length(ns) to 1 by -1 do
<span style="color: #0000FF;">{-</span><span style="color: #000000;">5795577</span><span style="color: #0000FF;">,-</span><span style="color: #000000;">62</span><span style="color: #0000FF;">,</span> <span style="color: #008000;">"Phix"</span><span style="color: #0000FF;">}}</span>
integer k = find(ns[i],digits)-1
if k=-1 or k>-b then return "invalid digit" end if
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">tests</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
total += k*bb
<span style="color: #0000FF;">{</span><span style="color: #004080;">atom</span> <span style="color: #000000;">n</span><span style="color: #0000FF;">,</span> <span style="color: #004080;">atom</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #004080;">string</span> <span style="color: #000000;">e</span><span style="color: #0000FF;">}</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">tests</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]</span>
bb *= b
<span style="color: #004080;">string</span> <span style="color: #000000;">ns</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">encodeNegBase</span><span style="color: #0000FF;">(</span><span style="color: #000000;">n</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
end for
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"%9d in base %-3d is %6s\n"</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">{</span><span style="color: #000000;">n</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">ns</span><span style="color: #0000FF;">})</span>
return total
<span style="color: #004080;">atom</span> <span style="color: #000000;">nn</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">decodeNegBase</span><span style="color: #0000FF;">(</span><span style="color: #000000;">ns</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
end function
<span style="color: #004080;">string</span> <span style="color: #000000;">ok</span> <span style="color: #0000FF;">=</span> <span style="color: #008080;">iff</span><span style="color: #0000FF;">(</span><span style="color: #000000;">ns</span><span style="color: #0000FF;">=</span><span style="color: #000000;">e</span> <span style="color: #008080;">and</span> <span style="color: #000000;">nn</span><span style="color: #0000FF;">=</span><span style="color: #000000;">n</span><span style="color: #0000FF;">?</span><span style="color: #008000;">""</span><span style="color: #0000FF;">,</span><span style="color: #008000;">" ????"</span><span style="color: #0000FF;">)</span>
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"%9d &lt;--------------'%s\n"</span><span style="color: #0000FF;">,{</span><span style="color: #000000;">nn</span><span style="color: #0000FF;">,</span><span style="color: #000000;">ok</span><span style="color: #0000FF;">})</span>
-- decimal, base, expected
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
constant tests = {{10, -2, "11110"},
<!--</syntaxhighlight>-->
{146, -3, "21102"},
{15, -10, "195"},
{-5795577,-62, "Phix"}}
 
procedure main()
atom n,b
string e
for i=1 to length(tests) do
{n,b,e} = tests[i]
string ns = encodeNegBase(n, b)
printf(1,"%9d in base %-3d is %6s\n", {n, b, ns})
atom nn = decodeNegBase(ns, b)
string ok = iff(ns=e and nn=n?""," ????")
printf(1,"%9d <--------------'%s\n",{nn,ok})
end for
end procedure
main()</lang>
{{out}}
<pre>
Line 1,374 ⟶ 1,767:
=={{header|Python}}==
 
<langsyntaxhighlight lang="python">#!/bin/python
from __future__ import print_function
 
Line 1,416 ⟶ 1,809:
print (result)
if DecodeNegBase(result, -10) == 15: print ("Converted back to decimal")
else: print ("Error converting back to decimal")</langsyntaxhighlight>
 
{{out}}
Line 1,428 ⟶ 1,821:
195
Converted back to decimal</pre>
 
=={{header|Quackery}}==
 
<syntaxhighlight lang="quackery"> [ dup dip /mod
over iff
[ - dip 1+ ]
else drop ] is /mod+ ( n n --> n n )
 
[ over 0 = iff
[ 2drop $ "0" ]
done
temp put
$ "" swap
[ temp share /mod+
digit
rot join swap
dup 0 = until ]
drop
temp release ] is ->negabase$ ( n n --> $ )
 
[ over $ "0" = iff
[ 2drop 0 ]
done
temp put
0 swap
witheach
[ dip
[ temp share * ]
char->n + ]
temp release ] is negabase$-> ( $ n --> n )
 
10 dup echo say " -> "
-2 ->negabase$ dup echo$ say " -> "
-2 negabase$-> echo cr
146 dup echo say " -> "
-3 ->negabase$ dup echo$ say " -> "
-3 negabase$-> echo cr
15 dup echo say " -> "
-10 ->negabase$ dup echo$ say " -> "
-10 negabase$-> echo cr</syntaxhighlight>
 
{{out}}
 
<pre>10 -> 11110 -> 10
146 -> 21102 -> 146
15 -> 195 -> 15
</pre>
 
=={{header|Racket}}==
 
<langsyntaxhighlight lang="racket">#lang racket
 
(define all-digits (string->list "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz-"))
Line 1,489 ⟶ 1,929:
 
(define-values (->hexadecimal hexadecimal->) (negabase-convertors 16))
(check-equal? (->hexadecimal 31) "1F"))</langsyntaxhighlight>
 
{{out}}
Line 1,510 ⟶ 1,950:
Note that the parse-base routine will handle 'illegal' negative negative-base values without blowing up.
 
<syntaxhighlight lang="raku" perl6line>multi sub base ( Int $value is copy, Int $radix where -37 < * < -1) {
my $result;
while $value {
Line 1,561 ⟶ 2,001:
 
# 'Illegal' negative-base value
say q| '-21'.&parse-base(-10) = |, '-21'.&parse-base(-10);</langsyntaxhighlight>
{{out}}
<pre> 4.&base( -4) = 130 : '130'.&parse-base( -4) = 4
Line 1,585 ⟶ 2,025:
Doing pretty much the same tests as the explicit version.
 
<syntaxhighlight lang="raku" perl6line>use Base::Any;
 
for < 4 -4 0 -7 10 -2 146 -3 15 -10 -19 -10 107 -16
Line 1,593 ⟶ 2,033:
printf "%21s.&to-base\(%5d\) = %-11s : %13s.&from-base\(%5d\) = %s\n",
+$v, $r, $nbase, "'$nbase'", $r, $nbase.&from-base($r);
}</langsyntaxhighlight>
{{out}}
<pre> 4.&to-base( -4) = 130 : '130'.&from-base( -4) = 4
Line 1,612 ⟶ 2,052:
<br>negative base back to the original number in base ten &nbsp; (and issues an error message if not correct).
===handles up to base -10===
<langsyntaxhighlight lang="rexx">/*REXX pgm converts & displays a base ten integer to a negative base number (up to -10).*/
@=' converted to base '; numeric digits 300 /*be able to handle ginormous numbers. */
n= 10; b= -2; q= nBase(n, b); say right(n, 20) @ right(b, 3) '────►' q ok()
Line 1,640 ⟶ 2,080:
p= p + 1 /*bump the power by 1. */
end /*j*/ /* [↓] process the number "bottom-up".*/
return $</langsyntaxhighlight>
{{out|output|text=&nbsp; when using the default inputs:}}
<pre>
Line 1,654 ⟶ 2,094:
<br>because the symbols (glyphs or numerals) used herein may not be in the same exact order. &nbsp; The symbols represented
<br>in this REXX program should be able to represent almost any programming language used on Rosetta Code.
<langsyntaxhighlight lang="rexx">/*REXX pgm converts & displays a base ten integer to a negative base number (up to -71).*/
@=' converted to base '; numeric digits 300 /*be able to handle ginormous numbers. */
n= 10; b= -2; q= nBase(n, b); say right(n, 20) @ right(b,3) '────►' q ok()
Line 1,686 ⟶ 2,126:
$= $ + v * r**p; p= p + 1 /*add it to $ (result); bump power by 1*/
end /*j*/ /* [↑] process the number "bottom-up".*/
return $</langsyntaxhighlight>
{{out|output|text=&nbsp; when using the default inputs:}}
<pre>
Line 1,698 ⟶ 2,138:
 
=={{header|Ring}}==
<langsyntaxhighlight lang="ring">
# Project : Negative base numbers
 
Line 1,738 ⟶ 2,178:
next
return svect
</syntaxhighlight>
</lang>
{{out}}
<pre>
Line 1,748 ⟶ 2,188:
195 decoded in base -10 = 15
</pre>
=={{header|RPL}}==
{{trans||Python}}
« → base
« '''IF''' DUP NOT '''THEN''' →STR
'''ELSE'''
""
'''WHILE''' OVER '''REPEAT'''
base MOD LASTARG / FLOOR
'''IF''' OVER 0 < '''THEN'''
1 + SWAP
base -
'''ELSE''' SWAP '''END'''
ROT +
'''END''' SWAP DROP
» » '<span style="color:blue">→NEGB</span>' STO
« → nstr base
« 0
1 nstr SIZE '''FOR''' j
base *
nstr j DUP SUB STR→ +
'''NEXT'''
» » '<span style="color:blue">NEGB→</span>' STO
« { 10 -2 146 -3 15 -10 } → cases
« 1 cases SIZE '''FOR''' j
cases j GET cases j 1 + GET <span style="color:blue">→NEGB</span>
DUP cases j 1 + GET <span style="color:blue">NEGB→</span>
2 '''STEP'''
cases SIZE →LIST
» » '<span style="color:blue">TASK</span>' STO
{{out}}
<pre>
1: { "11110" 10 "21102" 146 "195" 15 }
</pre>
 
=={{header|Ruby}}==
{{trans|Julia}}
{{works with|Ruby|2.3}}
<syntaxhighlight lang="ruby">DIGITS = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'
 
# convert a base 10 integer into a negative base value (as a string)
 
def negative_base_encode(n, b)
raise 'base out of range' if (b < -62) || (b > -2)
return '0' if n == 0
revdigs = []
while n != 0 do
n, r = n.divmod(b)
if r < 0
n += 1
r -= b
end
revdigs << r
end
return revdigs.reduce('') { |digstr, digit| DIGITS[digit] + digstr }
end
 
# convert a negative base value (as a string) into a base 10 integer
 
def negative_base_decode(n, b)
raise 'base out of range' if (b < -62) || (b > -2)
value = 0
n.reverse.each_char.with_index do |ch, inx|
value += DIGITS.index(ch) * b**inx
end
return value
end
 
# do the task
 
[ [10, -2], [146, -3], [15, -10], [0, -31], [-6221826, -62] ].each do |pair|
decimal, base = pair
encoded = negative_base_encode(decimal, base)
decoded = negative_base_decode(encoded, base)
puts("Enc: %8i base %-3i = %5s base %-3i Dec: %5s base %-3i = %8i base %-3i" %
[decimal, 10, encoded, base, encoded, base, decoded, 10])
end</syntaxhighlight>
{{out}}
<pre>Enc: 10 base 10 = 11110 base -2 Dec: 11110 base -2 = 10 base 10
Enc: 146 base 10 = 21102 base -3 Dec: 21102 base -3 = 146 base 10
Enc: 15 base 10 = 195 base -10 Dec: 195 base -10 = 15 base 10
Enc: 0 base 10 = 0 base -31 Dec: 0 base -31 = 0 base 10
Enc: -6221826 base 10 = Ruby base -62 Dec: Ruby base -62 = -6221826 base 10</pre>
 
=={{header|Rust}}==
{{trans|Go}}
<langsyntaxhighlight lang="rust">const DIGITS: [char;62] = ['0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z'];
 
Line 1,799 ⟶ 2,323:
}
return out.chars().rev().collect();
}</langsyntaxhighlight>
 
 
=={{header|Scala}}==
<langsyntaxhighlight lang="scala">object NegativeBase {
val digits = ('0' to '9') ++ ('a' to 'z') ++ ('A' to 'Z')
Line 1,825 ⟶ 2,349:
}._1
}
}</langsyntaxhighlight>
 
<langsyntaxhighlight lang="scala">def testConversion(b: Int)(n: Int, s: String): Unit = {
println(s"$n in base -$b = ${NegativeBase.intToStr(n, b)}")
println(s"$s from base -$b = ${NegativeBase.strToInt(s, b)}")
Line 1,835 ⟶ 2,359:
testConversion(3)(146, "21102")
testConversion(10)(15, "195")
testConversion(62)(795099356, "Scala")</langsyntaxhighlight>
 
{{out}}
Line 1,849 ⟶ 2,373:
 
=={{header|Seed7}}==
<langsyntaxhighlight lang="seed7">$ include "seed7_05.s7i";
 
const string: DIGITS is "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
Line 1,919 ⟶ 2,443:
doCheck(15, -10);
doCheck(404355637, -62);
end func;</langsyntaxhighlight>
 
{{out}}
Line 1,936 ⟶ 2,460:
{{trans|Raku}}
{{trans|Python}}
<langsyntaxhighlight lang="ruby">func EncodeNegBase(Num n, Num b { .~~ (-36 .. -2) }) {
var out = []
var r = 0
Line 1,972 ⟶ 2,496:
# Extra
say ("25334424 in base -31: ", EncodeNegBase(25334424, -31))
say ("sidef from base -31: ", DecodeNegBase("sidef", -31))</langsyntaxhighlight>
{{out}}
<pre>
Line 1,989 ⟶ 2,513:
=={{header|VBA}}==
{{trans|Modula-2}}
<langsyntaxhighlight lang="vb">Const DIGITS = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
Dim Str(63) As String
Private Function mod2(a As Long, b As Integer) As Long
Line 2,054 ⟶ 2,578:
Driver 15, -10
Driver 118492, -62
End Sub</langsyntaxhighlight>
{{out}}
<pre>10 encoded in base -2 = 11110
Line 2,071 ⟶ 2,595:
{{trans|Kotlin}}
{{libheader|Wren-fmt}}
<langsyntaxhighlight ecmascriptlang="wren">import "./fmt" for Fmt
 
var digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
Line 2,109 ⟶ 2,633:
var n = decodeNegBase.call(ns, p[1])
Fmt.print("$8s decoded in base $-3d = $d\n", ns, p[1], n)
}</langsyntaxhighlight>
 
{{out}}
Line 2,127 ⟶ 2,651:
 
=={{header|zkl}}==
<langsyntaxhighlight lang="zkl">fcn toNBase(n,radix){
var [const] cs=[0..9].chain(["a".."z"]).pump(String); //"0123456789abcd..z"
_assert_(-37 < radix < -1,"invalid radix");
Line 2,141 ⟶ 2,665:
fcn toInt(str,radix){ // the toInt(radix) method radix is 2..36
str.reduce('wrap(s,d,rdx){ s*radix + d.toInt(rdx); },0,radix.abs());
}</langsyntaxhighlight>
<langsyntaxhighlight lang="zkl">ns:=T( T(10,-2), T(146,-3), T(15,-10), T(107,-16), T(41371458,-36), T(44661,-36) );
results:=ns.pump(List,Void.Xplode,toNBase);
foreach nb,r in (ns.zip(results)){
_,b:=nb;
println("%10d.base(%3d) = \"%s\" --> %d".fmt(nb.xplode(),r,toInt(r,b)));
}</langsyntaxhighlight>
{{out}}
<pre>
1,150

edits