容斥原理
1 #include <iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<algorithm> 5 #include<stdlib.h> 6 #include<vector> 7 using namespace std; 8 int p[110],g,f[55],q[55],o,vis[55],pa[55],n,kk; 9 #define LL long long 10 void init() 11 { 12 int i,j; 13 for(i = 2; i < 50 ; i++) 14 if(!f[i]) 15 for(j = i+i ; j < 50 ; j+=i) 16 f[j] = 1; 17 for(i = 2; i < 50 ; i++) 18 if(!f[i]) 19 p[++g] = i; 20 } 21 LL find(int num,int k) 22 { 23 if(num<k) return 0; 24 int i,x=k; 25 LL s = 1; 26 for(i = 1; i <= k ; i++) 27 { 28 s*=num; 29 num--; 30 while(x>1&&s%x==0) 31 { 32 s/=x; 33 x--; 34 } 35 } 36 return s; 37 } 38 LL dfs(int k,int v,int a) 39 { 40 int i,j; 41 LL s=0; 42 if(a==o+1&&v==k) 43 { 44 for(i = 1; i <= n ; i++) 45 { 46 for(j = 1; j <= v ; j++) 47 if(i%pa[j]!=0) 48 break; 49 if(j==v+1) 50 s++; 51 } 52 s = find(s,kk); 53 return s; 54 } 55 if(a>o) return 0; 56 pa[v+1] = p[a]; 57 s+=dfs(k,v+1,a+1); 58 s+=dfs(k,v,a+1); 59 return s; 60 } 61 int main() 62 { 63 int i,j; 64 init(); 65 cin>>kk>>n; 66 LL s=0; 67 for(i = 1; i <= g ; i++) 68 { 69 int num = 0; 70 for(j = 2; j <= n ; j++) 71 if(j%p[i]==0) 72 num++; 73 if(num<kk) continue; 74 q[++o] = p[i]; 75 s+=find(num,kk); 76 } 77 for(i = 2; i <= o ; i++) 78 { 79 memset(vis,0,sizeof(vis)); 80 LL pp=dfs(i,0,1); 81 if(i%2==0) 82 s-=pp; 83 else 84 s+=pp; 85 } 86 if(s>=10000) 87 cout<<"10000"<<endl; 88 else 89 cout<<s<<endl; 90 return 0; 91 }