CodeForces 507D 数位dp(n位的数满足该数的一个后缀是k的倍数有多少个)

灵活!

首先,需要从后向前dfs,因为后缀。

然后,不用再加limit了,但是在特殊的位置要知道该位加的是0还是1。

这样的话,记住后缀mod k的值,就很好dfs了。

dfs(pod,preMOD,flag)

 1 #include<stdio.h>
 2 #include<string.h>
 3 int dp[1005][105][2],shi[1005];
 4 int k,MOD,n;
 5 int dfs(int pos,int preMOD,int flag)
 6 {
 7     int tmp,i,ans=0;
 8     if (pos>n) return flag;
 9     if (dp[pos][preMOD][flag]!=-1)
10         return dp[pos][preMOD][flag];
11     tmp=(pos==n?1:0);
12     for (i=tmp;i<=9;i++)
13         ans=(ans+dfs(pos+1,(preMOD+i*shi[pos-1])%k,
14               flag||((preMOD+i*shi[pos-1])%k==0&&i!=0)))%MOD;
15     return dp[pos][preMOD][flag]=ans;
16 }
17 int main()
18 {
19     int cnt,i;
20     scanf("%d%d%d",&n,&k,&MOD);
21     shi[0]=1;
22     for (i=1;i<=1000;i++) shi[i]=shi[i-1]*10%k;
23     memset(dp,-1,sizeof(dp));
24     printf("%d\n",dfs(1,0,0));
25 }
View Code

题目链接:http://codeforces.com/contest/507/problem/D

转载于:https://www.cnblogs.com/xiao-xin/articles/4245372.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值