题目
分析
对于20%,
ans=Πni=1Πnj=igcd(ai,ai+1,...,aj−1,aj)
显然这是会超时的,那么我们换个方法,
假设当前做到 i ,设
那么
ans=ans∗ai∗Πi−1j=1gcd(bj,ai)
发现 b 一定是单调递增的,而且,其中有很多的
那么,就可以加个链表。
时间复杂度 O(NlogN) 。
#include <cmath>
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <queue>
const long long maxlongint=2147483647;
const long long mo=1000000009;
const long long N=50005;
using namespace std;
long long a[N],ans=1,n,m,b[N],tot,v[N];
long long gcd(long long x,long long y)
{
return x==0?y:gcd(y%x,x);
}
long long mi(long long x,long long y)
{
long long sum=1;
while(y)
{
if(y&1) sum=sum*x%mo;
x=x*x%mo;
y/=2;
}
return sum;
}
int main()
{
freopen("ned.in","r",stdin);
freopen("ned.out","w",stdout);
scanf("%lld",&n);
for(long long i=1;i<=n;i++)
{
scanf("%lld",&a[i]);
b[i]=a[i];
v[i]=i;
}
ans=a[1];
for(long long i=2;i<=n;i++)
{
ans=ans*a[i]%mo;
long long k=i;
for(long long j=i-1;j;j=v[j]-1)
{
b[j]=gcd(b[j],a[i]);
if(b[j]==b[k])
v[k]=v[j];
ans=ans*mi(b[j],j-v[j]+1)%mo;
k=j;
}
}
printf("%d",ans);
}