rt,一直 60 分 WA 爆,其中 dfs 部分是 P6754 的 AC 代码。
思路是判断有多少个数不是萌数,然后用区间长度减掉答案。
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int MOD = 1e9 + 7;
const int N = 1000 + 10;
string s, t;
ll l, r, dgt[N], f[N][2][12][12];
ll dp(int len, int op, int is0, ll lst1, ll lst2){
if(!len) return 1;
if(!is0 && f[len][op][lst1][lst2] != -1) return f[len][op][lst1][lst2];
ll cnt = 0; int k = (op ? dgt[len] : 9);
for(int d=0;d<=k;d++){
if(d == lst1 || d == lst2) continue;
if(is0 && d == 0) (cnt += dp(len - 1, op & (d == k), 1, lst1, lst2)) %= MOD;
else (cnt += dp(len - 1, op & (d == k), 0, d, lst1)) %= MOD;
}
if(!is0) f[len][op][lst1][lst2] = cnt;
return cnt;
}
ll solve(ll x){
if(x == -1) return 0;
int len = 0;
do dgt[++len] = x % 10;
while(x /= 10);
memset(f, -1, sizeof(f));
return dp(len, 1, 1, 10, 10) % MOD;
}
int main(){
cin >> s >> t;
for(int i=0;i<s.length();i++) l = (l * 10 + (s[i] - '0')) % MOD;
for(int i=0;i<t.length();i++) r = (r * 10 + (t[i] - '0')) % MOD;
ll ans = (solve(r) - solve(l - 1)) % MOD;
ans = (ans + MOD) % MOD;
printf("%lld\n", ((r - l + 1 - ans) % MOD + MOD) % MOD);
return 0;
}