算法竞赛—进制转换题目

进制转换是由一组数码符号和两个基本因素 “基数” 与 “位权” 构成的。基数是指,进位计数制中所采用的数码(数制中用来表示“量”的符号)的个数。位权是指,进位制中每一固定位置对应的单位值。例如:2进制数中,2是基数,第1位的位权为2,第2位的位权为4,第3位的位权为8。

主要知识点:

  1. c++中取模运算的规律
  2. 不同进制之间的转换
  3. 十进制数与负数进制之间的转换

1. 关于进制

我们可以这样理解十进制:将每个阿拉伯数字乘以一个以该数字所处位置为指数,以10为底数的幂之和的形式。例如 123可表示为 1×102+2×101+3×100=100+20+3=123.

2. 在c++中负数取模为负数,模的符号取决于被除数。

int main(){
    int x,y,z,w;
    x=8%5;
    y=8%-5;
    z=-8%5;
    w=-8%-5;
    cout<<x<<" "<<y<<" "<<z<<" "<<w;
}

显示结果:
在这里插入图片描述

进制转换1

题目来源:洛谷P2084
输入N、M 输出:将M进制的数N转换成十进制表示的式子
eg: 输入:2 10101
输出:1×24+1×23+1×20

int m;			//进制转换 系数为0时,该单项式要省略
char c[1001];   //往往用字符串来存n进制数
int main(){
    scanf("%d ",&m);		// 表示M进制
    cin>>c;   
    for (int i=0;i<strlen(c);i++){
     if(i!=0&&c[i]!='0') printf("+");  //只要不是第一个数且系数不为0 就要先输出 +
     if(c[i]=='0') continue;
      printf("%c*%d^%d",c[i],m,strlen(c)-i-1);//strlen(c)-i-1可以从大到小表示指数
    }
    return 0;
}

进制转换2

题目来源:洛谷P1143
输入n、n进制的数、m 。输出:m进制对应的数
从数学思维上来讲,最好理解的方法是:先转换成10进制(根据位值原理),再取模运算,将10进制转换为m进制 。
样例:
输入:16 FF
输出:11111111

string a;
int n,m,c[1000000],i,j=0,x,sum;
int main(){
    cin>>n;
    cin>>a;
    cin>>m;
    for(int i=0;i<a.size();i++){
        if(a[i]<'A'){   //0-9可以直接-'0'得出对应的数码值
            x=pow(n,a.size()-i-1);
            x*=(a[i]-'0');
            sum+=x;
        }
        else{    //A-F
            x=pow(n,a.size()-1-i);
            x*=(a[i]-'A'+10);
            sum+=x;
        }
    }
    while(sum>0){   //十进制转m进制 权值从小到大存余数
        c[j++]=sum%m;
        sum/=m;
    }
    for(i=j-1;i>=0;i--){  //模拟数学思想输出,注:此处不可用字符串函数来表示长度,因为c[]是整型数组
        if(c[i]<10) printf("%d",c[i]);
        else printf("%c",c[i]+'A'-10);
    }
    return 0;
}

进制转换3

题目来源:洛谷P1017
输入:十进制数的n、R。 输出:此负进制数及其基数
将整数n转换成R进制。任何一个正整数R 或一个负整数−R 都可以被选来作为一个数制系统的基数。如果是以R 或−R 为基数,则需要用到的数码为 0,1,…R-1。
、eg:2和==-2==所用的数码都是0、1。
-15(十进制) 相当于 110001(-2进制)
1×(-2)5+ 1×(-2)4+ 0×(-2)3+ 0×(-2)2+ 0×(-2)1+ 1×(-2)0=-15
样例:2800 -16
输出:28800=19180(base-16)
注:此处可用第一部分的结论, 在c++中负数取模为负数,此题输出结果不可为负数,必须先进行等值转化。

/*负数的进制转换--正数的进制转换*/
void turn(int n,int r){
    if(n==0) return ;    //递归结束
    int m=n%r;  //输出的余数不可<0
    if(m<0) m-=r,n+=r;    //如果余数小于0,转化为正数
    if(m<10) m+='0';  //转化成字符串存储
    else m='A'+m-10;
    turn(n/r,r);   //通过递归得出所有余数
    printf("%c",m);  //注意:因为结果为余数倒序,输出要写在递归后,否则会顺序输出
    return ;
}
int main(){
    int n,r;
    cin>>n>>r;   //n表示要转换的数 r是进制数
    cout<<n<<"=";
    turn(n,r);
    printf("(base%d)",r);
    return 0;
}

注:个人喜好原因,只展示代码的核心部分,不喜勿喷。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值