P1100 高低位交换

摘要:就是让你把一个数的二进制凑够32位然后从中间劈开交换,再转换成十进制。

我一开始写这道题的时候,思路就是很暴力的把他们拆开,补零,交换转成10进制(用了好多字符串)。

代码如下:

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
unsigned long long a,ans=0,sum=0,shi=0;
string h,l,hh,ll,ha;//这是一堆字符串
int main(){
    scanf("%u",&a);
    while(a>0){
        if(sum<16){//判断如果现在的位数小于16
            h[ans]=a%2+'0';//就把这个存在字符串h里面
        }
        if(ans==16){
            ans=0;//ans起到的是下标的作用
        }
        if(sum>=16){//判断如果现在的位数小于16
            l[ans]=a%2+'0';//就把这个存在字符串h里面
        }
        a/=2;
        ans++;
        sum++;
    }
    if(sum>=16&&ans<16){//补零
        for(int i=ans;i<16;i++){
            l[i]='0';//我也不知道我当时怎么想的,好像是觉得两个如果都没有满16,那就做两个判断,都补上零。
        }
    }
    if(sum<16&&ans<16){//依然是补零
        for(int i=ans;i<16;i++){
            h[i]='0';
        }
        for(int i=0;i<16;i++){
            l[i]='0';
        }
    }
    sum=0;//用字符串ha把他们两个交换着存过来
    for(int i=16-1;i>=0;i--){
        ha[sum]=h[i];
        sum++;
    }
    for(int i=16-1;i>=0;i--){
        ha[sum]=l[i];
        sum++;
    }
    ans=1;
    sum=0;
    int i=0;
    for(int i=32-1;i>=0;i--){//倒着把他们输出出来
        shi+=(ha[i]-'0')*ans;
        ans*=2;
    }
    printf("%u",shi);
    return 0;
}

结果很悲惨,不仅没A只得了90不说,我改来改去都把自己给改迷糊了。于是我就重新构思了一下,写了下面的代码,就AC了。

#include<iostream>
#include<cstdio>
using namespace std;
unsigned long long n,shu[10010],ans=0,shi=0;
int main(){
    scanf("%u",&n);
    while(n>0){//转二进制,没有用一个字符串,用的数组。因为数组不仅很方便,甚至连补零那一步都省了,因为数组它本身默认值就是0嘛,所以就可以直接转成十进制。
        shu[ans]=n%2;
        n/=2;
        ans++;
    }
    ans=1;
    for(int i=16;i<32;i++){
        shi+=shu[i]*ans;
        ans*=2;
    }//先把后面的16位转成10进制。
    for(int i=0;i<16;i++){
        shi+=shu[i]*ans;
        ans*=2;
    }//再把前面的16位转成10进制,记得要用一个变量,不然就变成两个数了
    printf("%u\n",shi);//最后输出就好啦
    return 0;
}

重写的代码:大致思路就是把转化成的二进制存到一个数组里(因为数组默认都是0,所以就直接省去补零这一步了,直接算就好了),一定要记得先算后面的再算前面的!!

做完不久后我又知道了一个东西:左移和右移运算符(跟异或是一套的)

仅仅只用几行就可以把这道题A掉。

代码如下

#include<iostream>
#include<cstdio>
int n;
int main(){
    scanf("%d",&n);
    printf("%d\n",(n>>16)+(n<<16));
    //>>是把这个数转为二进制右移(而且他还会自动补零!!)
    //<<相反就是把这个数的二进制往左移喽(依然会自动补零)
    return 0;
}

加上注释一共10行,所以建议追求代码简洁的一定要去学学位运算,可以省去好多劲儿。

虽然这个这么简单的代码把我写了好久的代码给秒杀了,但是我并不是很伤心,因为学会了这个以后肯定在别的地方可以用到。

以上为我这道题的全部思路与解法,如果有什么不对的地方,还请各位大佬及时向我纠正。

原文地址:https://www.cnblogs.com/dgdger/p/12848928.html