ACWING number of months / Luo Gu similar distribution

Thinking

In general, digital DP can do with search in mind, we consider this question in mind search

First, find the numbers and, to judge whether the sum of the digits is divisible His idea is wrong, because each number should be judged once, remember search becomes violent search.

Convert ideas, divisible is the modulus is zero, so you can consider the modulus of each step to work out, count to determine the last digit is 0 to modulus

But we do not know how much you figures and is it? It does not matter, do not know enough to enumerate . You figures and small, direct enumeration of violence, when the last search to determine whether the value and enumeration.


C ++ code

#include<bits/stdc++.h>
using namespace std;
#define go(i,a,b) for(int i=(a);i<=(b);++(i))
#define com(i,a,b) for(int i=(a);i>=(b);--(i))
#define mem(a,b) memset((a),(b),sizeof(a))
#define inf 0x3f3f3f3f
#define fin freopen("input.txt","r",stdin)
#define fout freopen("output.txt","w",stdout)
typedef long long ll;
const int maxn=100010;
int num[20],n,p;
ll f[20][200][200],_pow[20];

ll dfs(int len,int sum,bool limit,int mod){
    if(!len){
        if(sum==p&&!mod) return 1;
        return 0;
    }
    if(!limit&&f[len][sum][mod]!=-1) return f[len][sum][mod];
    int up=limit?num[len]:9;
    ll ret=0;
    go(i,0,up){
        ret+=dfs(len-1,sum+i,limit&&i==num[len],(mod*10+i)%p);
    }
    return f[len][sum][mod]=ret;
}

ll solve(ll val){
    n=0;
    while(val){
        num[++n]=val%10;
        val/=10;
    }
    ll ans=0;
    for(p=1;p<=200;p++)
    mem(f,-1),ans+=dfs(n,0,1,0);
    return ans;
}

signed main(){ 
    //fin;
    ll a,b;
    scanf("%lld%lld",&a,&b);
    printf("%lld",solve(b)-solve(a-1));
    return 0;
}

Guess you like

Origin www.cnblogs.com/White-star/p/11469671.html