目录
零、所涉及的库函数介绍
1.STL中的栈stack
因为下面转换所用的“除N取余,将余数逆向输出”的方法,栈结构先进后出的特性非常适用。
常用操作:
2.数学库函数math.h
主要用其中的乘法运算函数pow(x,y)表示以x为底,y为幂
注意:这里x,y必须为数值型才可进行数值计算
3.字符串函数string.h
主要使用里面的strlen()函数来返回字符串的长度
一、二进制与十进制互转
1.二进制转十进制
方法:把二进制数按照权值展开,相加即得十进制数
图示:
代码:
//二进制转十进制
#include<iostream>
#include<string.h>
#include<math.h>
#include<stack>
using namespace std;
int main(){
stack<char>s;
char n[100];
long long int number=0;
scanf("%s",n);
for(int j=0;j<strlen(n);j++){
s.push(n[j]);//将所输入的二进制字符串的逐个元素依次进栈
}
int length=s.size();//保存栈的初始长度
for(int i=0;i<length;i++){
number+=(s.top()-'0')*pow(2,i);//因为栈中元素为字符型,要转换成相应的数制才能进行乘方运算
s.pop();//栈顶元素出栈,即删除。栈长度减去一
}
printf("%lld",number);
return 0;
}
2.十进制转二进制
方法:除2取余法,即不断对2取余,最后将余数逆向输出
图示:
代码:
//十进制转换成二进制,除2取余法
#include<iostream>
#include<stack>
using namespace std;
int main(){
stack<int>s;
int n,j;
cin>>n;
while(n>0){
s.push(n%2);
n/=2;
}
j=s.size();//提前保存初始化过后栈的长度,因为下面栈的长度是动态变化的
for(int i=0;i<j;i++){
printf("%d",s.top());//输出栈顶元素
s.pop();//删除栈顶元素
}
return 0;
}
二、八进制与十进制互转
1.八进制转十进制
方法:将八进制数按照权值展开,相加即得十进制数
图示:
代码:
//八进制转十进制
#include<iostream>
#include<string.h>
#include<math.h>
#include<stack>
using namespace std;
int main(){
stack<char>s;
char n[10];
long long int number=0;
scanf("%s",n);
for(int j=0;j<strlen(n);j++){
s.push(n[j]);
}
int length=s.size();
for(int i=0;i<length;i++){
number+=(s.top()-'0')*pow(8,i);
s.pop();
}
printf("%lld",number);
return 0;
}
2.十进制转八进制
方法:除8取余法,余数逆向输出
图示:
代码:
//十进制转换成八进制,除8取余法
#include<iostream>
#include<stack>
using namespace std;
int main(){
stack<int>s;
int j;
long long int n;
cin>>n;
while(n>0){
s.push(n%8);
n/=8;
}
j=s.size();//提前保存初始化过后栈的长度,因为下面栈的长度是动态变化的
for(int i=0;i<j;i++){
printf("%d",s.top());//输出栈顶元素
s.pop();//删除栈顶元素
}
return 0;
}
三、十六进制与十进制互转
1.十六进制转十进制
方法:同样是按权值展开,然后相加。不过十六进制有些特殊,因为它是由0~9,A~F所组成,A~F分别对应十进制中的10~15。所以在展开是要判断它是字母还是数字,然后以ASCII码值相减的方法得到其对应的数值,进行乘方运算。
图示:
代码:
//十六进制转十进制
#include<iostream>
#include<string.h>
#include<math.h>
#include<stack>
using namespace std;
int main(){
stack<char>s;
char n[10];
long long int number=0;
scanf("%s",n);
for(int j=0;j<strlen(n);j++){
s.push(n[j]);
}
int length=s.size();
for(int i=0;i<length;i++){
if((int)s.top()>64)//这里是ASCII码值的比较,A的ASCII码值为65
number+=(s.top()-'A'+10)*pow(16,i);//因为栈空间里存储的是字符,要将字符转换成数值才能进行乘方运算
else
number+=(s.top()-'0')*pow(16,i);
s.pop();
}
printf("%lld",number);
return 0;
}
2.十进制转十六进制
方法:除16取余法,注意余数大于9的情况
图示:
代码:
//十进制转换成十六进制
#include<iostream>
#include<stack>
using namespace std;
int main(){
stack<int>s;
int n,j;
cin>>n;
if(n==0)
printf("%d",n);
else{
while(n>0){
s.push(n%16);
n/=16;
}
j=s.size();//提前保存初始化过后栈的长度,因为下面栈的长度是动态变化的
for(int i=0;i<j;i++){
if(s.top()>9){
printf("%c",'A'+s.top()-10);
}
else{
printf("%d",s.top());
}
s.pop();
}
}
return 0;
}
四、其它进制的互转
可以以十进制为中转站,例如二进制转八进制。可以先将二进制转换为十进制,再将十进制转换为 八进制,达到转换的目的。如下方有向图所示,各个进制间是连通的,都有一条有向路径,使得彼此互联,即所有进制间互相都能够完成直接或者间接地转换。
例子:十六进制转换成八进制
输入说明:第一个数n为行数,接下来输入n行十六进制的正整数
输出说明:输出对应的n行八进制数字
注:当遇到位数较大的输入时,数据将会发生溢出。(后续解决)
代码:
#include<iostream>
#include<stack>
#include<string.h>
#include<math.h>
using namespace std;
typedef struct shiliu{
char s[100001];
}SL;
long long int Ten(char a[],long long int len){
stack<char>s1;
long long int i,j,number=0;
for(j=0;j<len;j++){
s1.push(a[j]);
}
int length=s1.size();
for(i=0;i<length;i++){
if((int)s1.top()>64)//这里是ASCII码值的比较,A的ASCII码值为65
number+=(s1.top()-'A'+10)*pow(16,i);
else
number+=(s1.top()-'0')*pow(16,i);
s1.pop();
}
return number;
}
int main(){
int i,j,n;
long long int n10;
cin>>n;
SL a[n];
stack<int>s2;
for(i=0;i<n;i++)
scanf("%s",a[i].s);
for(i=0;i<n;i++){
n10=Ten(a[i].s,strlen(a[i].s));//先转换成十进制数
//再转换成对应的八进制数字
while(n10>0){
s2.push(n10%8);
n10/=8;
}
j=s2.size();//提前保存初始化过后栈的长度,因为下面栈的长度是动态变化的
for(int i=0;i<j;i++){
printf("%d",s2.top());
s2.pop();//删除栈顶元素
}
printf("\n");
}
return 0;
}
五、总结
(1)10进制转换为N进制,常采用“除N取余法”,最后将余数逆向输出。
(2)N进制转换成10进制,常采用按权值展开,最后相加的方法得到对应的十进制数。
(3)基于以上特性,采用C++STL库中的栈stack作为存储结构最为合适,效率高且简洁。
(4)所有进制间的互转,可以采用以10进制为中转站(当然也可以采用其它进制),实现进制的间接转换。
(5)由于输入都是以字符串的形式输入的,所以栈空间类型是字符型,那么取出时即是一个字符,要通过ASCII码值相减的方式将其转换成对应的数值,才能使用pow()函数进行乘方运算。这一点很容易被忽略,导致出错。
都看到最后了,不妨点个赞啦~
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/93507.html