状压DP,f[i][j]表示在i状态下余数为j的情况
然后就是i的表示。。先认为数字互不相同(坑爹的想法= =),然后就有没有用到压缩状态
然后还要去重。。对每个数字来说除以数字个数的阶乘即可
1 #include<bits/stdc++.h> 2 #define inc(i,l,r) for(int i=l;i<=r;i++) 3 #define dec(i,l,r) for(int i=l;i>=r;i--) 4 #define link(x) for(edge *j=h[x];j;j=j->next) 5 #define mem(a) memset(a,0,sizeof(a)) 6 #define inf 1e9 7 #define ll long long 8 #define succ(x) (1<<x) 9 #define NM 15 10 using namespace std; 11 int read(){ 12 int x=0,f=1;char ch=getchar(); 13 while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();} 14 while(isdigit(ch))x=x*10+ch-'0',ch=getchar(); 15 return x*f; 16 } 17 char st[NM]; 18 int a[NM],b[NM],d[succ(NM)][1005],s,T,t,n,m; 19 int main(){ 20 freopen("data.in","r",stdin); 21 T=read(); 22 while(T--){ 23 mem(d);mem(a);mem(b);s=1; 24 scanf("%s",st+1);t=read(); 25 n=strlen(st+1); 26 inc(i,1,n){ 27 a[i]=st[i]-'0'; 28 b[a[i]]++; 29 } 30 m=succ(n)-1;d[0][0]=1; 31 inc(i,0,m) 32 inc(j,0,t-1)if(d[i][j]) 33 inc(k,1,n) 34 if((i&succ(k-1))==0) 35 d[i|succ(k-1)][(j*10+a[k])%t]+=d[i][j]; 36 /*inc(i,0,m){ 37 inc(j,0,t-1)printf("%d ",d[i][j]);printf("\n"); 38 }*/ 39 inc(i,0,9) 40 inc(j,1,b[i])s*=j; 41 printf("%d\n",d[m][0]/s); 42 } 43 return 0; 44 }