向前走莫回头❤

【NOIP 模拟题】[T2]分解数(线性筛+贪心)

【题解】【线性筛+贪心】

【通过分析题意我们能够得出:分解数为当前最小公倍数的质因数个数-1。】

【先用线性筛筛出10^7内的质数,同时记录10^7内的每个数的最小质因子,然后把每个数分解质因数,并存下来。】

【枚举有>=k个不同质因数的区间,枚举区间的右端点,维护左端点的区间[L,R],保证在[L,R]区间中,不同的质因数个数>=k,当区间的右端点不断右移时,区间的左端点区间也只会不断右移,即左端点区间的位置是单调的。这样就可以线性处理】

【用两个桶维护左端点在L和R时不同质因数的个数,当左端点区间满足条件,将R-L+1加入答案】

#include<cstdio>
#include<cstring>
#include<algorithm>
#define mod 10007
#define N 1e7
using namespace std;
int prime[670000],minn[10000005];
int cnt[1000005][10],nm1[1000005],nm2[1000005];
int n,k,tt1,tt2,left,right,ans;
inline void shai()
{
	for(int i=2;i<=N;++i)
	 {
	 	if(!minn[i]) prime[++prime[0]]=i,minn[i]=prime[0];
	 	for(int j=1;j<=prime[0];++j)
	 	 {
	 	 	if(i*prime[j]>N) break;
	 	 	if(minn[i]<j) minn[i*prime[j]]=minn[i];
	 	 	 else minn[i*prime[j]]=j;
	 	 	if(!(i%prime[j])) break;
		  }
	 }
}
int main()
{
	freopen("dec.in","r",stdin);
	freopen("dec.out","w",stdout);
	int i,j;
	shai();
	scanf("%d%d",&n,&k);
	for(i=1;i<=n;++i)
	 {
	 	int x;
	 	scanf("%d",&x);
	 	while(x!=1)
	 	 {
	 	 	int t=minn[x];
	 	 	int p=prime[t];
	 	 	cnt[i][++cnt[i][0]]=t;
	 	 	while(!(x%p)) x/=p;
		  }
	 }
	left=right=1; 
	k++;
	for(i=1;i<=n;++i)
	 {
	 	for(j=1;j<=cnt[i][0];++j)
	 	 {
	 	 	if(!nm1[cnt[i][j]]) tt1++;
	 	 	nm1[cnt[i][j]]++;
	 	 	if(!nm2[cnt[i][j]]) tt2++;
	 	 	nm2[cnt[i][j]]++;
		  }
		if(tt1>=k)
		 {
		 	while(tt1>k)
		     {
		  	    for(j=1;j<=cnt[left][0];++j)
		  	     {
		  	 	    nm1[cnt[left][j]]--;
		  	 	    if(!nm1[cnt[left][j]]) tt1--;
			     }
			    left++;
		    }
		    if(tt1==k)
	         {
	     	    while(1)
	     	     {
	     	 	    for(j=1;j<=cnt[right][0];++j)
	     	 	     {
	     	 	 	    nm2[cnt[right][j]]--;
	     	 	 	    if(!nm2[cnt[right][j]]) tt2--;
				     }
				    if(tt2<k)
				     {
				 	    for(j=1;j<=cnt[right][0];++j)
				 	     {
				 	 	    if(!nm2[cnt[right][j]]) tt2++;
				 	 	    nm2[cnt[right][j]]++;
					     }
					    break;
				     }
				    right++;
			    }
			    if(right>=left) ans=(ans+(right-left+1)%mod)%mod;
		    }
		 }
	 }
	printf("%d\n",ans);
	return 0;
}


posted @ 2016-11-10 07:27  lris0-0  阅读(109)  评论(0编辑  收藏  举报
过去的终会化为美满的财富~o( =∩ω∩= )m