主题:超麻烦的进制转换问题。
问题描述:
输入 m<n>p ,m为数字串,n为该数字串的进制(位数不超过200位),p为转换后的进制。
输入示例
10<2>10
输出示例
2
我的想法:首先将n进制数字串转化为高精度的十进制,再将十进制转化为p进制。
局部源代码(无变量等):
procedure readata;
begin
read(ch);lenm:=0;
while ch<>'<' do
begin
inc(lenm);
m[k]:=ord(ch)-48;
read(ch); //转化成高精度的n进制。
end;
for i:=1 to lenm div 2 do begin t:=m[i]; m[i]:=m[lenm+i-1]; m[lenm+i-1]:=t; end;
//将其逆置容易计算
read(ch);
k:=1;n:=0;
while ch<>'>' do
begin
n:=n+(ord(ch)-48)*k; //读入n
k:=k*10;
end;
read(ch);
k:=1;n:=0;
while not eof do
begin
n:=n+(ord(ch)-48)*k; //类似的读入p
end;
end;
begin (将子程序放在下方容易观看)
s[1]:=0;lens:=1;
for i:=1 to lenm do
begin //转换公式s:=s+m[i]*n^i-1;
lenst:=1;st[1]:=1; //先算n^i-1
sq(st,i-1);
chen(st,lenst,m[i]); //再算m[i]*n^i-1
jia(s,st); //最后算s+m[i]*n^i-1
end;
k:=0;
repeat
inc(k);
d[k]:=getmo(s,p); //求余p来得出p进制的数
divide(s,p); //整除s来进一步得出p进制的数
until (s[1]=0)and(lens=1); //直到s为0为止
for i:=k downto 1 do write(d[i]); //应逆序输出
readln;
end.
procedure chen(var a:array;var lena:integer; x:integer;); //高精度乘以低精度
begin
for i:=1 to lena do a[i]:=a[i]*x+a[i-1]div 10;
if a[lena]>=10 then begin inc(lena); a[lena]:=a[lena-1]div 10;
for i:=1 to lena do a[i]:=a[i] mod 10;
end;
procedure sq(n:integer); //计算m^i-1
begin
for i:=1 to n do
chen(st,lenst,p);
end;
procedure jia(var a:arr;b:arr); //高精度加高精度
begin
if lens>lenst then len:=lens
else len:=lenst;
for i:=1 to len do a[i]:=a[i]+b[i]+a[i-1]div 10;
if a[len]>=10 then begin inc(len); a[len]:=a[len-1]div 10;
for i:=1 to len do a[i]:=a[i] mod 10;
end;
function getmo(a:arr,x:integer); //高精度求余
begin
v:=0;
for i:=lens downto 1 do
begin
w:=v*10+a[i];
v:=w mod x;
end;
getmo:=v;
end;
procedure divide(var a:arr;x:integer);//高精度整除
begin
v:=0;
for i:=lens downto 1 do
begin
w:=v*10+a[i];
v:=w mod x;
a[i]:=w div x;
end;
while (lens>1)and(a[lens]=0) do dec(lens);
end;
小弟刚学高精度不久,不大熟练,可是这题实在太麻烦了,运行时总不知是哪里的原理错误,若其中有错误,望高手指教
输入 m<n>p ,m为数字串,n为该数字串的进制(位数不超过200位),p为转换后的进制。
输入示例
10<2>10
输出示例
2
我的想法:首先将n进制数字串转化为高精度的十进制,再将十进制转化为p进制。
局部源代码(无变量等):
procedure readata;
begin
read(ch);lenm:=0;
while ch<>'<' do
begin
inc(lenm);
m[k]:=ord(ch)-48;
read(ch); //转化成高精度的n进制。
end;
for i:=1 to lenm div 2 do begin t:=m[i]; m[i]:=m[lenm+i-1]; m[lenm+i-1]:=t; end;
//将其逆置容易计算
read(ch);
k:=1;n:=0;
while ch<>'>' do
begin
n:=n+(ord(ch)-48)*k; //读入n
k:=k*10;
end;
read(ch);
k:=1;n:=0;
while not eof do
begin
n:=n+(ord(ch)-48)*k; //类似的读入p
end;
end;
begin (将子程序放在下方容易观看)
s[1]:=0;lens:=1;
for i:=1 to lenm do
begin //转换公式s:=s+m[i]*n^i-1;
lenst:=1;st[1]:=1; //先算n^i-1
sq(st,i-1);
chen(st,lenst,m[i]); //再算m[i]*n^i-1
jia(s,st); //最后算s+m[i]*n^i-1
end;
k:=0;
repeat
inc(k);
d[k]:=getmo(s,p); //求余p来得出p进制的数
divide(s,p); //整除s来进一步得出p进制的数
until (s[1]=0)and(lens=1); //直到s为0为止
for i:=k downto 1 do write(d[i]); //应逆序输出
readln;
end.
procedure chen(var a:array;var lena:integer; x:integer;); //高精度乘以低精度
begin
for i:=1 to lena do a[i]:=a[i]*x+a[i-1]div 10;
if a[lena]>=10 then begin inc(lena); a[lena]:=a[lena-1]div 10;
for i:=1 to lena do a[i]:=a[i] mod 10;
end;
procedure sq(n:integer); //计算m^i-1
begin
for i:=1 to n do
chen(st,lenst,p);
end;
procedure jia(var a:arr;b:arr); //高精度加高精度
begin
if lens>lenst then len:=lens
else len:=lenst;
for i:=1 to len do a[i]:=a[i]+b[i]+a[i-1]div 10;
if a[len]>=10 then begin inc(len); a[len]:=a[len-1]div 10;
for i:=1 to len do a[i]:=a[i] mod 10;
end;
function getmo(a:arr,x:integer); //高精度求余
begin
v:=0;
for i:=lens downto 1 do
begin
w:=v*10+a[i];
v:=w mod x;
end;
getmo:=v;
end;
procedure divide(var a:arr;x:integer);//高精度整除
begin
v:=0;
for i:=lens downto 1 do
begin
w:=v*10+a[i];
v:=w mod x;
a[i]:=w div x;
end;
while (lens>1)and(a[lens]=0) do dec(lens);
end;
小弟刚学高精度不久,不大熟练,可是这题实在太麻烦了,运行时总不知是哪里的原理错误,若其中有错误,望高手指教