題目
n(2<=n<=1e5)個數的數組a[],滿足ai(1<=ai<=2e5)
求gcd({lcm({ai,aj}) | i<j}),
即對任意兩個不同下標(i,j),求其最小公倍數lcm(i,j)
再對這C(n,2)個結果,求其最大公約數gcd
思路來源
題解
題解
1600的題也要總結,我也太廢物了吧……
①一個比較直觀好做的做法,枚舉素因子pi,
考慮pi在至少n-1個數中都出現纔可以被保留下來,否則兩個pi的0次冪其gcd一定爲1
如果在n個數中均出現,答案是次小的冪次,
如果在n-1個數中出現,說明最小的冪次是0,即
②真正想總結的是這個做法,
考慮n=3,
把含a1項搞出來,求個gcd,含a2項搞出來求個gcd,…,之後再兩兩求gcd
先給結論:
證這個結論,可以考慮對每個素因子證,gcd是對冪次取min,lcm是取max
等價於證
於是分還是大於,討論一下就證完了
有了化簡之後的式子,維護一個後綴gcd,就做完了
代碼
#include<bits/stdc++.h>
using namespace std;
#define rep(i,a,b) for(int i=(a);i<=(b);++i)
#define per(i,a,b) for(int i=(a);i>=(b);--i)
#define sci(a) scanf("%d",&(a))
typedef long long ll;
const int N=1e5+10;
ll lcm(ll x,ll y){
return x/__gcd(x,y)*y;
}
int n;
ll a[N],suf[N],ans;
int main(){
sci(n);
rep(i,1,n){
scanf("%lld",&a[i]);
}
suf[n]=a[n];
per(i,n-1,1){
suf[i]=__gcd(suf[i+1],a[i]);
}
ans=lcm(a[1],suf[2]);
rep(i,2,n-1){
ans=__gcd(ans,lcm(a[i],suf[i+1]));
}
printf("%lld\n",ans);
return 0;
}