【51nod 1203】【JZPLCM】【莫队算法】
2017-02-23 17:21
148 查看
题目大意
给出一列数,求一段区间的lcm。
解题思路
离线询问,对小于sqrt(n)的质因子暴力求出,rmq解决询问。这样之后就只最多剩下一个质因子,可以使用莫队用桶维护。
code
#include<cmath> #include<cstdio> #include<cstring> #include<algorithm> #define LF double #define LL long long #define Min(a,b) ((a<b)?a:b) #define Max(a,b) ((a>b)?a:b) #define Fo(i,j,k) for(int i=j;i<=k;i++) #define Fd(i,j,k) for(int i=j;i>=k;i--) using namespace std; int const Mxn=5*1e4; int N,Q,Size,A[Mxn+9],Ha[Mxn+9],Cnt[Mxn+9],F[Mxn+9][17],Two[17],Ans[Mxn+9],Mo=1e9+7; struct Rec{int L,R,P;}; Rec B[Mxn+9]; bool Cmp(Rec X,Rec Y){ return ((X.L-1)/Size<(Y.L-1)/Size)||(((X.L-1)/Size==(Y.L-1)/Size)&&(X.R<Y.R)); } int Pow(LL X,int Y){ LL Z=1; while(Y){ if(Y&1)Z=Z*X%Mo; X=X*X%Mo; Y>>=1; } return Z; } int Calc(int L,int R){ int X=log(R-L+1)/log(2); return Max(F[L][X],F[R-Two[X]+1][X]); } int main(){ freopen("d.in","r",stdin); freopen("d.out","w",stdout); scanf("%d%d",&N,&Q);int Mx=0,Mx2=log(N)/log(2),Tmp,Ok;Size=sqrt(N); Two[0]=1;Fo(i,1,Mx2)Two[i]=Two[i-1]<<1; Fo(i,1,N)scanf("%d",&A[i]),Mx=Max(Mx,A[i]);Mx=sqrt(Mx); Fo(i,1,Q)scanf("%d%d",&B[i].L,&B[i].R),B[i].P=i,Ans[i]=1; Fo(i,2,Mx){ Tmp=sqrt(i);Ok=1; Fo(j,2,Tmp)if(i%j==0){Ok=0;break;} if(Ok){ Fo(j,1,N){ F[j][0]=0; while(A[j]%i==0)F[j][0]++,A[j]/=i; } Fo(k,1,Mx2)Fd(j,N-Two[k-1],1)F[j][k]=Max(F[j][k-1],F[j+Two[k-1]][k-1]); Fo(j,1,Q)Ans[j]=1ll*Ans[j]*Pow(i,Calc(B[j].L,B[j].R))%Mo; } } sort(B+1,B+Q+1,Cmp); int Next;LL Now; Fo(i,1,Q)if(((B[i].L-1)/Size!=(B[i-1].L-1)/Size)||(i==1)){ if(B[i].P==14){ int bb; bb++; } Now=1;Next=(B[i].L-1)/Size*Size+Size; Fo(j,1,Mxn)Cnt[j]=0; Fo(j,Next+1,B[i].R){ if(!Cnt[A[j]])Now=(Now*A[j])%Mo; Cnt[A[j]]++; } LL Tmp=Now; Fo(j,B[i].L,Min(Next,B[i].R)){ if(!Cnt[A[j]])Now=(Now*A[j])%Mo; Cnt[A[j]]++; } Fo(j,B[i].L,Min(Next,B[i].R))Cnt[A[j]]--; Ans[B[i].P]=1ll*Ans[B[i].P]*Now%Mo;Now=Tmp; }else{ if(B[i].P==14){ int bb; bb++; } Fo(j,Max(Next+1,B[i-1].R+1),B[i].R){ if(!Cnt[A[j]])Now=(Now*A[j])%Mo; Cnt[A[j]]++; } LL Tmp=Now; Fo(j,B[i].L,Min(Next,B[i].R)){ if(!Cnt[A[j]])Now=(Now*A[j])%Mo; Cnt[A[j]]++; } Fo(j,B[i].L,Min(Next,B[i].R))Cnt[A[j]]--; Ans[B[i].P]=1ll*Ans[B[i].P]*Now%Mo;Now=Tmp; } Fo(i,1,Q)printf("%d\n",Ans[i]); return 0; }
相关文章推荐
- 51nod 1203 JZPLCM 莫队算法
- 51Nod 1203 JZPLCM
- 51nod 1203 JZPLCM 离线 + 树状数组
- [51nod 1203]JZPLCM
- 51nod 1203 JZPLCM
- 51nod 1203 jzplcm
- 51Nod-1203-JZPLCM
- 51 nod 1203 JZPLCM
- 【51 Nod 1203】JZPLCM
- [51nod1203]JZPLCM
- 51nod 1592 数列积 莫队算法+树状数组
- 【TsinsenA1339】JZPLCM(顾昱洲) 树状数组
- 51Nod1203 2012集训队答辩 JZPLCM
- 莫队算法讲解
- 51Nod 2006 飞行员配对(二分图最大匹配) 匈牙利算法
- 莫队算法(NBUT1457 Sona)
- CodeForces 375D Tree and Queries 莫队算法
- 51nod二级算法题全部题解
- pl/sql 实现归并算法
- 【莫队算法】[HDU5145]NPY and girls