hdu 5491 The Next(暴力枚举)

Problem Description
Let L denote the number of 1s in integer D’s binary representation. Given two integers S1 and S2, we call D a WYH number if S1≤L≤S2.
With a given D, we would like to find the next WYH number Y, which is JUST larger than D. In other words, Y is the smallest WYH number among the numbers larger than D. Please write a program to solve this problem.
 
Input
The first line of input contains a number T indicating the number of test cases (T≤300000).
Each test case consists of three integers D, S1, and S2, as described above. It is guaranteed that 0≤D<231 and D is a WYH number.

 

 
Output
For each test case, output a single line consisting of “Case #X: Y”. X is the test case number starting from 1. Y is the next WYH number.

 

 

 

Sample Input
3
11 2 4
22 3 3
15 2 5

 

 

 

Sample Output
Case #1: 12 
Case #2: 25 
Case #3: 17

 

 

 

Source
 

不想写,找了个别人的.

思路:

考虑通过比较当前的1的数目来进行最小的数的修正。

先将D加1,然后计算出D的1的数目tot,这时候比较tot和s1,s2的大小,这时候有两种情况:

1、tot<s1,这时我需要增加1的数目,因为要最小,所以我从右开始找到一个0(位置假设为i),将D加上2^i。

2、tot>s2,这时我需要减少1的数目,所以我从右开始找到一个1,将D加上2^i。

如此循环上述过程,直到符合tot符合s1,s2的条件。

上面操作的原因是:我加上2^i,就是将那一位由1变为0或者由0变为1,而我是从右边开始寻找的,可以保证每次所做的改变都是最小的。同时我的D是一直增加的,所以当条件满足时,就是那个最小的。

 

 1 #pragma comment(linker, "/STACK:1024000000,1024000000")
 2 #include<iostream>
 3 #include<cstdio>
 4 #include<cstring>
 5 #include<cmath>
 6 #include<math.h>
 7 #include<algorithm>
 8 #include<queue>
 9 #include<set>
10 #include<bitset>
11 #include<map>
12 #include<vector>
13 #include<stdlib.h>
14 #include <stack>
15 using namespace std;
16 int dirx[]={0,0,-1,1};
17 int diry[]={-1,1,0,0};
18 #define PI acos(-1.0)
19 #define max(a,b) (a) > (b) ? (a) : (b)
20 #define min(a,b) (a) < (b) ? (a) : (b)
21 #define ll long long
22 #define eps 1e-10
23 #define MOD 1000000007
24 #define N 100
25 #define inf 1e12
26 ll d,s1,s2;
27 ll num[N];
28 ll k;
29 ll count_(ll dd){
30    memset(num,0,sizeof(num));
31    ll cnt=0;
32    k=0;
33        while(dd){
34            if(dd&1) cnt++;
35            num[k++]=(dd&1);
36            dd>>=1;
37        }
38        num[k++]=0;
39 
40    return cnt;
41 }
42 int main()
43 {
44    ll ac=0;
45    ll t;
46    scanf("%I64d",&t);
47    while(t--){
48        scanf("%I64d%I64d%I64d",&d,&s1,&s2);
49 
50        ll dd=d+1;
51 
52        while(1){
53            ll tmp=count_(dd);
54 
55            if(tmp<s1){
56               for(ll i=0;i<k;i++){
57                   if(num[i]==0){
58                      dd+=(1<<i);
59                      break;
60                   }
61               }
62            }else if(tmp>s2){
63               for(ll i=0;i<k;i++){
64                   if(num[i]==1){
65                      dd+=(1<<i);
66                      break;
67                   }
68               }
69            }else{
70               break;
71            }
72        }
73        printf("Case #%I64d: ",++ac);
74        printf("%I64d\n",dd);
75 
76    }
77     return 0;
78 }
View Code

 

posted @ 2015-10-01 18:45  UniqueColor  阅读(339)  评论(0编辑  收藏  举报