POJ-3252 Round Numbers (数位DP)

Round Numbers

http://poj.org/problem?id=3252

Time Limit: 2000MS   Memory Limit: 65536K
     

Description

The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone‘ (also known as ‘Rock, Paper, Scissors‘, ‘Ro, Sham, Bo‘, and a host of other names) in order to make arbitrary decisions such as who gets to be milked first.
They can‘t even flip a coin because it‘s so hard to toss using hooves.

They have thus resorted to "round number" matching. The first cow picks an integer less than two billion. The second cow does the same. If the numbers are both "round numbers", the first cow wins,

otherwise the second cow wins.

A positive integer N is said to be a "round number" if the binary representation of N has as many or more zeroes than it has ones. For example, the integer 9, when written in binary form, is 1001. 1001 has two zeroes and two ones; thus,
9 is a round number. The integer 26 is 11010 in binary; since it has two zeroes and three ones, it is not a round number.

Obviously, it takes cows a while to convert numbers to binary, so the winner takes a while to determine. Bessie wants to cheat and thinks she can do that if she knows how many "round numbers" are in a given range.

Help her by writing a program that tells how many round numbers appear in the inclusive range given by the input (1 ≤ Start < Finish ≤ 2,000,000,000).

Input

Line 1: Two space-separated integers, respectively Start and Finish.

Output

Line 1: A single integer that is the count of round numbers in the inclusive range Start..Finish

Sample Input

2 12

Sample Output

6

题目大意:统计区间[sta,des]中,二进制表示下0的个数比1的个数多的数字总数(不含前导0)?

写完后看了很多题解,发现大家用数位DP都要用dfs,感觉直接循环也很好理解啊...

设dp[i][j][0]表示长度为i,含有j个0且最高位为0的数字的个数;dp[i][j][1]表示长度为i,含有j个0且最高位为1的数字的个数

初始:dp[1][0][1]=1;//长度为1,含有0个0且最高位为1的数字个数为1

dp[1][1][0]=1;//长度为1,含有1个0且最高位为0的数字个数为1

然后通过状态转移,预处理出所有的结果

最后再在函数中进行从高位到低位的按位统计

差不多有点感觉了,貌似数位DP都是先进性预处理,再按位统计即可

#include <cstdio>
#include <cstring>
#include <algorithm>

using namespace std;

int num[35],len,sta,des,ans,cnt[2];//cnt[i]表示该数二进制中从高位到当前位i出现的次数(i=0,1)
int dp[35][35][2];//dp[i][j][0]表示长度为i,含有j个0且最高位为0的数字的个数;dp[i][j][1]表示长度为i,含有j个0且最高位为1的数字的个数

void Init() {
    memset(dp,0,sizeof(dp));
    dp[1][0][1]=1;//长度为1,含有0个0且最高位为1的数字个数为1
    dp[1][1][0]=1;//长度为1,含有1个0且最高位为0的数字个数为1
    for(int i=2;i<=31;++i) {
        dp[i][0][1]=1;//长度为i,含有0个0且最高位为1的数字个数为1
        for(int j=1;j<=i;++j) {
            dp[i][j][0]=dp[i-1][j-1][0]+dp[i-1][j-1][1];//第i位取0,后i-1位中含有j-1个0,第i-1位既可取0,也可取1
            dp[i][j][1]=dp[i-1][j][0]+dp[i-1][j][1];//第i位取1,后i-1位中含有j个0,第i-1位既可取0,也可取1
        }
    }
}

int getCnt(int x) {//返回区间[1,x]中二进制表示下,0个数大于等于1个数的数字总数
    cnt[0]=cnt[1]=ans=len=0;
    while(x>0) {
        num[++len]=x%2;
        x/=2;
    }
    for(int i=len;i>1;--i) {
        for(int j=((i-1)>>1)+((i-1)&1);j<i;++j) {//从i起的高位都取0,第i-1位取1,后i-1位中0个数大于等于1个数的数字个数
            ans+=dp[i-1][j][1];
        }
        if(num[i]==1) {
            if(cnt[1]!=0) {
                for(int j=max(0,(len>>1)+(len&1)-1-cnt[0]);j<i;++j) {//从i+1起的高位与原数一样,第i位取0,后i-1位中0个数+已出现的0个数大于等于1个数+已出现的1个数
                    ans+=dp[i-1][j][0]+dp[i-1][j][1];
                }
            }
            ++cnt[1];
        }
        else {//当前位为0
            ++cnt[0];
        }
    }
    if(num[1]==1) {//如果最低位为1
        if(cnt[1]!=0) {//高位出现过1(即该数不是1)
            if(cnt[0]>cnt[1]) {//高位中0出现的次数多于1出现的次数,则当前位为0,1时均合法
                ans+=2;
            }
            else if(cnt[0]==cnt[1]) {//高位中0出现的次数等于1出现的次数,则当前位取0时合法
                ++ans;
            }
        }
    }
    else if(len>0) {//如果该数不为0,且当前位为0
        ++cnt[0];
        if(cnt[0]>=cnt[1]) {//该数中所有的0的个数大于1的个数,则此数合法
            ++ans;
        }
    }
    return ans;
}

int main() {
    Init();
    while(2==scanf("%d%d",&sta,&des)) {
        printf("%d\n",getCnt(des)-getCnt(sta-1));
    }
    return 0;
}
时间: 2024-10-09 05:50:19

POJ-3252 Round Numbers (数位DP)的相关文章

POJ 3252 Round Numbers(数位dp&amp;amp;记忆化搜索)

题目链接:[kuangbin带你飞]专题十五 数位DP E - Round Numbers 题意 给定区间.求转化为二进制后当中0比1多或相等的数字的个数. 思路 将数字转化为二进制进行数位dp,由于一个二进制数的最高位必须为1.所以设置变量first记录前面位是否有1,若有1,则可随意放,否则,仅仅可放1. 同一时候.上面的推断决定了搜索时len的大小与二进制本身的长度不一定相等,所以需两个变量对1和0的个数进行记录. 用dp[a][b][c]保存长度a,b个0,c个1的数字个数.记忆化搜索.

POJ 3252 Round Numbers (数位DP)

题意:求区间内一个数二进制位1的数量大于等于0的数的个数. 析:dp[i][j][k] 表示前 i 位,长度为 j 的,1的数量是 k.注意前导0. 代码如下: #pragma comment(linker, "/STACK:1024000000,1024000000") #include <cstdio> #include <string> #include <cstdlib> #include <cmath> #include <

POJ 3252 round numbers(数位DP)

#include <iostream> #include <cstdio> #include <cstdlib> #include <algorithm> #include <cmath> #include <vector> #include <queue> #include <cstring> #include <set> #include <stack> #include <m

POJ 3252 Round Numbers 数位dp(入门

题目链接:点击打开链接 题意: 给定一个区间,求区间内有多少个合法数(当这个数的二进制中0的个数>=1的个数称为合法数 二进制无前导0) 思路: cnt[i]表示二进制长度为i位(即最高位为1,其他位任意)时的合法数个数. sum[i] 就是二进制长度<=i位的合法数个数. 然后从最高位枚举到低位即可.维护当前0的个数. #include <cstdio> #include <algorithm> #include <cstring> #include &l

poj 3252 Round Number 数位dp

Round Numbers Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 11481   Accepted: 4305 Description The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone' (also known as 'Rock, Paper, Scissors',

POJ 3252 Round Numbers 数学题解

Description The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone' (also known as 'Rock, Paper, Scissors', 'Ro, Sham, Bo', and a host of other names) in order to make arbitrary decisions such as who gets

poj 3252 Round Numbers 【推导&#183;排列组合】

以sample为例子 [2,12]区间的RoundNumbers(简称RN)个数:Rn[2,12]=Rn[0,12]-Rn[0,1] 即:Rn[start,finish]=Rn[0,finish]-Rn[0,start-1] 所以关键是给定一个X,求出Rn[0,X] 现在假设X=10100100  这个X的二进制总共是8位,任何一个小于8位的二进制都小于X 第一部分,求出长度为[0,7]区间内的二进制是RoundNumber的个数  对于一个长度为Len的二进制(最高位为1),如何求出他的Rou

poj 3252 Round Numbers(数位DP)

Round Numbers Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 11003   Accepted: 4064 Description The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone' (also known as 'Rock, Paper, Scissors',

POJ 3252 Round Numbers

Round Numbers Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 12824   Accepted: 4946 Description The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone' (also known as 'Rock, Paper, Scissors',

POJ 3252 —— Round Numbers

Round Numbers Time Limit:2000MS     Memory Limit:65536KB     64bit IO Format:%I64d & %I64u Description The cows, as you know, have no fingers or thumbs and thus are unable to play Scissors, Paper, Stone' (also known as 'Rock, Paper, Scissors', 'Ro, S