编写一个程序,可以实现将一个数字由一个进制转换为另一个进制。
这里有 62 个不同数位 {0−9,A−Z,a−z}。
输入格式
第一行输入一个整数,代表接下来的行数。
接下来每一行都包含三个数字,首先是输入进制(十进制表示),然后是输出进制(十进制表示),最后是用输入进制表示的输入数字,数字之间用空格隔开。
输入进制和输出进制都在 2 到 62 的范围之内。
(在十进制下)A=10,B=11,…,Z=35,a=36,b=37,…,z=61(0−9 仍然表示 0−9)。
输出格式
对于每一组进制转换,程序的输出都由三行构成。
第一行包含两个数字,首先是输入进制(十进制表示),然后是用输入进制表示的输入数字。
第二行包含两个数字,首先是输出进制(十进制表示),然后是用输出进制表示的输入数字。
第三行为空白行。
同一行内数字用空格隔开。
输入样例:
8
62 2 abcdefghiz
10 16 1234567890123456789012345678901234567890
16 35 3A0C92075C0DBF3B8ACBC5F96CE3F0AD2
35 23 333YMHOUE8JPLT7OX6K9FYCQ8A
23 49 946B9AA02MI37E3D3MMJ4G7BL2F05
49 61 1VbDkSIMJL3JjRgAdlUfcaWj
61 5 dl9MDSWqwHjDnToKcsWE1S
5 10 42104444441001414401221302402201233340311104212022133030
输出样例:
62 abcdefghiz
2 11011100000100010111110010010110011111001001100011010010001
10 1234567890123456789012345678901234567890
16 3A0C92075C0DBF3B8ACBC5F96CE3F0AD2
16 3A0C92075C0DBF3B8ACBC5F96CE3F0AD2
35 333YMHOUE8JPLT7OX6K9FYCQ8A
35 333YMHOUE8JPLT7OX6K9FYCQ8A
23 946B9AA02MI37E3D3MMJ4G7BL2F05
23 946B9AA02MI37E3D3MMJ4G7BL2F05
49 1VbDkSIMJL3JjRgAdlUfcaWj
49 1VbDkSIMJL3JjRgAdlUfcaWj
61 dl9MDSWqwHjDnToKcsWE1S
61 dl9MDSWqwHjDnToKcsWE1S
5 42104444441001414401221302402201233340311104212022133030
5 42104444441001414401221302402201233340311104212022133030
10 1234567890123456789012345678901234567890
题意:将某个进制的数转换成另一个进制的数;
解法及思路:(要用到高精度)
一般的解法是将输入的进制数转换成10进制数,再将10进制数转换成另一个进制的数;
这里讲另一种解法,秦九绍进制转换(y总好像是这样说的,虽然我没搜到):
例如:将4进制的123转换成5进制的数,将1除以5,结果为0,余1,
再(1*4+2)除以5,结果为1,余1,再将(1*4+3)除以5,结果为1,余2;
则2表示4进制123在5进制下的最低位,11(上次除的结果),
再重复上述操作,结果为1,余0,再将1(上次除的结果)除以5,结果为0,余1;
所以102表示123在5进制下的数字; (图来自y总讲解)
假设输入进制为a,输出进制为b,xi表示输入的数的第i位,则运算规则为xn/b;
记录结果,(余数*a+x(n-1)) /b,记录结果,一直到不能除了;
最后的余数就是b进制下的第0位,上述除的结果之和去掉前导0再重复上述操作,
得到余数,为b进制的第1位,以此类推,直到除的结果为0;
’
(图片来自y总),看不懂的可以直接看 y总视频
#include<iostream>
#include<vector>
using namespace std;
int main()
{
int t;
cin>>t;
while(t--){
int a,b;
string a_s;//输入的字符串a进制数
vector<int>number;//反转存储a进制数每一位转换为10进制数
cin>>a>>b>>a_s;
for(int i=a_s.length()-1;i>=0;--i){//输入的a_s第一位表示的是高位,为了第一位存储低位,须反转存储;
if(a_s[i]>='0'&&a_s[i]<='9') number.push_back(a_s[i]-'0');
else if(a_s[i]>='A'&&a_s[i]<='Z') number.push_back(a_s[i]-'A'+10);
else number.push_back(a_s[i]-'a'+36);
}
vector<int>res;//存储b进制的每一位,
while(number.size()){//进行秦九绍循环除法;
int temp=0;//余数
for(int i=number.size()-1;i>=0;--i){
number[i]+=temp*a;
temp=number[i]%b;
number[i]/=b;
}//每一次的最后余数temp表示b进制的某一位数字;
res.push_back(temp);//每次存储b进制的一位数,从第0位开始存储;
while(number.size()&&number.back()==0) number.pop_back();//去除前导0;
}
cout<<a<<' '<<a_s<<endl;
cout<<b<<' ';
for(int i=res.size()-1;i>=0;--i){//输出要从高位输出,而且输出的是字符串;
if(res[i]>=0&&res[i]<=9) cout<<char(res[i]+'0');
else if(res[i]>=10&&res[i]<=35) cout<<char(res[i]-10+'A');
else cout<<char(res[i]-36+'a');
}
cout<<endl<<endl;
}
return 0;
}