• ural 1057 Amount of Degrees(数位DP)


    1057. Amount of Degrees

    Time limit: 1.0 second
    Memory limit: 64 MB
    Create a code to determine the amount of integers, lying in the set [X;Y] and being a sum of exactlyK different integer degrees of B.
    Example. Let X=15, Y=20, K=2, B=2. By this example 3 numbers are the sum of exactly two integer degrees of number 2:
    17 = 24+20,
    18 = 24+21,
    20 = 24+22.

    Input

    The first line of input contains integers X and Y, separated with a space (1 ≤ X ≤ Y ≤ 231−1). The next two lines contain integers K and B (1 ≤ K ≤ 20; 2 ≤ B ≤ 10).

    Output

    Output should contain a single integer — the amount of integers, lying between X and Y, being a sum of exactly K different integer degrees of B.

    Sample

    input output
    15 20
    2
    2
    
    3
    
    Problem Source: Rybinsk State Avia Academy

    题意:
    首先定义了一种数为特殊数。

    特殊数仅仅邮k个不同的b^x组成。

    如今问你[x,y]里有多少这种特殊数。

    思路:
    数位DP。

    dp[i][j]表示二进制表示中。前i为1的个数为j一共同拥有多少个数。其他进制类似处理。注意边界。

    具体见代码:
    #include<algorithm>
    #include<iostream>
    #include<string.h>
    #include<stdio.h>
    #include<stdlib.h>
    using namespace std;
    const int INF=0x3f3f3f3f;
    const int maxn=100010;
    typedef long long ll;
    int dp[35][35],base[35],bin[35];
    void init()
    {
        dp[0][0]=base[0]=1;
        for(int i=1;i<=32;i++)
        {
            dp[i][0]=1;
            base[i]=base[i-1]<<1;
            for(int j=1;j<=i;j++)
                dp[i][j]=dp[i-1][j]+dp[i-1][j-1];
        }
    }
    int calc(int x,int k)
    {
        int i,one=0,ans=0;
        for(i=31;i>=0;i--)
        {
            if(x&base[i])
            {
                if(one>k)
                    break;
                ans+=dp[i][k-one];
                one++;
                x-=base[i];
            }
        }
        if(one==k)
            ans++;
        return ans;
    }
    int getbin(int x,int b)
    {
        int ct=0,i,ret=0;
        if(!x)
            return x;
        while(x)
        {
            bin[ct++]=x%b;
            x/=b;
        }
        for(i=ct-1;i>=0;i--)
        {
            if(bin[i]>1)
                break;
            if(bin[i])
                ret=ret<<1|1;
            else
                ret<<=1;
        }
        while(i>=0)
        {
            ret=ret<<1|1;
            i--;
        }
        return ret;
    }
    int main()
    {
        int x,y,k,b;
    
        init();
        while(~scanf("%d%d%d%d",&x,&y,&k,&b))
        {
            y=getbin(y,b);
            x=getbin(x-1,b);
            printf("%d
    ",calc(y,k)-calc(x,k));
        }
        return 0;
    }
    


  • 相关阅读:
    java后台打开浏览器代码
    java国际化
    Struts2之action 之 感叹号 ! 动态方法调用
    ssh框架总结之action接收参数的三种方式
    电脑开机过程
    4.18quaternion rotation
    4.2
    "hello,world"lena
    bash 简介
    SCHEDULE
  • 原文地址:https://www.cnblogs.com/blfshiye/p/5056707.html
Copyright © 2020-2023  润新知