题意:求大于该整数且与该整数的二进制形式中'1'的个数相同的最小整数
思路:先将该数二进制化,再从0位开始枚举每一位,找到第一个i位为1 ,i+1位为0的位置,停止 ,将两位互换,再将访问过的1全部移到最右边 就是答案
特殊情况:注意只有最高位为1的情况。
//题意:求大于该整数且与该整数的二进制形式中'1'的个数相同的最小整数
//思路:先将该数二进制化,再从0位开始枚举每一位,找到第一个i位为1 ,i+1位为0的位置,停止
//将两位互换,再将访问过的1全部移到最右边 就是答案
//特殊情况:注意只有最高位为1的情况。
#include<cstdio>
#include<string.h>
using namespace std;
//a[100]记录该数的二进制表达,b[100]用来存2的幂;
int a[100],b[1000];
int num=0;
//将2的幂存储起来,方便二进制转化成十进制
void init(){
b[0]=1;
for(int i=1;i<=20;i++){
b[i]=b[i-1]*2;
}
}
//解决函数
void solve(int k){
//ans是记录最高位
int ans=0;
memset(a,0,sizeof(a));
int m2=0;
//十进制转化成二进制
while(k){
a[ans++]=k%2;
if(k%2==0)num++;
k/=2;
}
int m=0;int ans1=0;//ans1记录1的个数
//枚举二进制数
for(int i=0;i<ans;i++){
//找到符合要求的就停止
if(a[i]==1&&a[i+1]==0){
a[i]=0;a[i+1]=1;
m=i;
if(i==ans-1)ans++;//特殊情况只有最高位为1
break;
}
if(a[i]==1)ans1++;
}
//将之前的1全部提前
for(int i=0;i<=m;i++){//由于访问了m位,有ans1个1,第m+1位要占一个1,只需将由零位起的ans1-1位全部赋值为1,其余为零就行
if(i<ans1)a[i]=1;
else a[i]=0;
}
//二进制转化成十进制
for(int i=0;i<ans;i++){
if(a[i]==1){
m2+=b[i];
}
}
printf("%d\n",m2);
}
int main(){
int k;
init();
while(~scanf("%d",&k)&&k!=0){
solve(k);
}
}