• HDU 3555 Bomb(数位DP)


    Bomb

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 131072/65536 K (Java/Others)
    Total Submission(s): 3362    Accepted Submission(s): 1185


    Problem Description
    The counter-terrorists found a time bomb in the dust. But this time the terrorists improve on the time bomb. The number sequence of the time bomb counts from 1 to N. If the current number sequence includes the sub-sequence "49", the power of the blast would add one point.
    Now the counter-terrorist knows the number N. They want to know the final points of the power. Can you help them?
     
    Input
    The first line of input consists of an integer T (1 <= T <= 10000), indicating the number of test cases. For each test case, there will be an integer N (1 <= N <= 2^63-1) as the description.

    The input terminates by end of file marker.
     
    Output
    For each test case, output an integer indicating the final points of the power.
     
    Sample Input
    3 1 50 500
     
    Sample Output
    0 1 15
    Hint
    From 1 to 500, the numbers that include the sub-sequence "49" are "49","149","249","349","449","490","491","492","493","494","495","496","497","498","499", so the answer is 15.
     
    Author
    fatboy_cw@WHU
     
    Source
     
    Recommend
    zhouzeyong
     
     
     
     
    简单的数位DP入门题。
    注释见代码:
    /*
     * HDU 3555
     * 求1~N中含有数字49的个数     1 <= N <= 2^63-1
     */
    #include <iostream>
    #include <stdio.h>
    #include <string.h>
    #include <algorithm>
    using namespace std;
    long long dp[25][3];
    /*
     * dp[i][0],表示不含有49
     * dp[i][1],表示不含有49,且最高位为9
     * dp[i][2],表示含有49
     */
    void init()
    {
        dp[0][0]=1;
        dp[0][1]=dp[0][2]=0;
        for(int i=1;i<25;i++)
        {
            dp[i][0]=10*dp[i-1][0]-dp[i-1][1];//在前面加0~9的数字,减掉在9前面加4
            dp[i][1]=dp[i-1][0];//最高位加9
            dp[i][2]=10*dp[i-1][2]+dp[i-1][1];//在本来含有49的前面加任意数,或者在9前面加4
        }
    }
    int bit[25];
    long long calc(long long n)
    {
        int len=0;
        while(n)
        {
            bit[++len]=n%10;
            n/=10;
        }
        bit[len+1]=0;
        bool flag=false;
        long long ans=0;
        for(int i=len;i>=1;i--)
        {
            ans+=dp[i-1][2]*bit[i];
            if(flag)ans+=dp[i-1][0]*bit[i];
            else
            {
                if(bit[i]>4)ans+=dp[i-1][1];
            }
            if(bit[i+1]==4&&bit[i]==9)flag=true;
        }
        if(flag)ans++;//加上n本身
        return ans;
    }
    int main()
    {
        //freopen("in.txt","r",stdin);
        //freopen("out.txt","w",stdout);
        int T;
        long long n;
        scanf("%d",&T);
        init();
        while(T--)
        {
            scanf("%I64d",&n);
            printf("%I64d\n",calc(n));
        }
        return 0;
    }
     
     
    人一我百!人十我万!永不放弃~~~怀着自信的心,去追逐梦想
  • 相关阅读:
    第三次实验总结
    实验总结
    自我介绍
    BGP学习笔记
    source insight用于C语言编程的工具脚本
    LevelDB源码剖析
    LevelDB源码之五Current文件Manifest文件版本信息
    LevelDB源码之六缓存机制
    LevelDB源码之四LOG文件
    jQuery向动态生成的内容添加事件响应
  • 原文地址:https://www.cnblogs.com/kuangbin/p/3052414.html
Copyright © 2020-2023  润新知