B-number(hdu 3652)

题意:找出1~n范围内含有13并且能被13整除的数字的个数

/*
    数位DP
    dp[i][j][0]表示i位数模13为j当前没有包含13并且最高位不为1的方案数;
    dp[i][j][0]表示i位数模13为j当前没有包含13并且最高位为1的方案数; 
    dp[i][j][0]表示i位数模13为j当前包含13的方案数。
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#define N 15
using namespace std;
int bit[N],dp[N][N][3];
int dfs(int pos,int mod,int have,int lim){
    int num,ans,mod_x,have_x;
    if(pos<=0) return mod==0&&have==2;
    if(!lim&&dp[pos][mod][have]!=-1)
        return dp[pos][mod][have];
    num=lim?bit[pos]:9;
    ans=0;
    for(int i=0;i<=num;i++){
        mod_x=(mod*10+i)%13;
        have_x=have;
        if(have==0&&i==1) have_x=1;
        if(have==1&&i!=1) have_x=0;
        if(have==1&&i==3) have_x=2;
        ans+=dfs(pos-1,mod_x,have_x,lim&&i==num);
    }
    if(!lim) dp[pos][mod][have]=ans;
    return ans;
}
int main(){
    int n,len;
    while(scanf("%d",&n)!=EOF){
        memset(bit,0,sizeof(bit));
        memset(dp,-1,sizeof(dp));
        len=0;
        while(n){
            bit[++len]=n%10;
            n/=10;
        }
        printf("%d\n",dfs(len,0,0,1));
    }
    return 0;
}

 

posted @ 2017-04-21 22:20  karles~  阅读(243)  评论(0编辑  收藏  举报