传送门:beautiful number
题意:令 A=∑ni=1ai?10n?i(1≤ai≤9)(n为A的位数)。若A为“漂亮的数”当且仅当对于任意1≤i<n满足a[i]≥a[i+1]且对于任意1≤i≤n,i<j≤n,满足a[i] mod a[j]=0(例如931是一个“漂亮的数”而87不是),求在区间[L,R](包含L和R)里“漂亮的数”的个数。
分析:数位dp较为简单,dp[pos][pre]表示还有pos位且前一位数字是pre非限制条件下为漂亮数字的个数。
#pragma comment(linker,"/STACK:1024000000,1024000000") #include <cstdio> #include <cstring> #include <string> #include <cmath> #include <limits.h> #include <iostream> #include <algorithm> #include <queue> #include <cstdlib> #include <stack> #include <vector> #include <set> #include <map> #define LL long long #define mod 100000000 #define inf 0x3f3f3f3f #define eps 1e-6 #define N 410 #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 #define PII pair<int,int> using namespace std; inline LL read() { char ch=getchar();LL x=0,f=1; while(ch>‘9‘||ch<‘0‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch<=‘9‘&&ch>=‘0‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } LL dp[15][15]; int dig[15]; LL dfs(int pos,int pre,int limit,int fzore) { if(!pos)return 1; if(!limit&&~dp[pos][pre])return dp[pos][pre]; LL ans=0; int len=limit?dig[pos]:9; for(int i=0;i<=len;i++) { if(fzore) { ans+=dfs(pos-1,i,i==len&&limit,fzore&&!i); } if(i>pre||i==0)continue; if(pre%i==0) { ans+=dfs(pos-1,i,i==len&&limit,0); } } if(!limit)dp[pos][pre]=ans; return ans; } LL solve(LL n) { int len=0; while(n) { dig[++len]=n%10; n/=10; } return dfs(len,0,1,1); } int main() { int T; LL a,b; T=read(); memset(dp,-1,sizeof(dp)); while(T--) { a=read();b=read(); printf("%I64d\n",solve(b)-solve(a-1)); } }
时间: 2024-11-09 01:49:02