题目链接:点击打开链接


题解思路:天真的我以为只要一次两两gcd就是答案了,然而这明显是错的,例如:18*12,12*42,42*18这三个数要是一次两两gcd的话是不会得到6的。所以要用gcd完得到的数再去和数组的数去gcd然后看有没有新的数出现。


代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int mx = 1e3+10;
int n,m,a[mx];
bool vis[mx];
int _gcd(int a,int b)
{
    return b==0?a:_gcd(b,a%b);
}
int main()
{
    int t;
    scanf("%d",&t);
    while(t--){
        scanf("%d",&n);
        for(int i=0;i<n;i++) scanf("%d",a+i);
        memset(vis,0,sizeof(vis));
        for(int i=0;i<n;i++){
            for(int j=i+1;j<n;j++)
            vis[_gcd(a[i],a[j])] = 1;
        }
        bool flag = 1;
        int len = 1;
        while(flag&&len<n-2){
            flag = 0;
            len++;
            for(int i=1;i<mx;i++) if(vis[i])
            for(int j=0;j<n;j++){
                if(!vis[_gcd(i,a[j])]) flag = 1;
                vis[_gcd(i,a[j])] = 1;
            }
        }
        flag = 0;
        for(int i=1;i<mx;i++){
            if(vis[i]){
                if(flag) putchar(' ');
                printf("%d",i);
                flag = 1;
            }
        }
        puts("");
    }
    return 0;
}