ARC122E

ARC122E

题目大意:
重排序列 \(\{a_i\}\) ,使前缀 \(\operatorname{lcm}\) 递增。

限制最紧的一定是最后一个数,因此从后往前放数。
考虑如何判断一个数是否能作为结尾。
显然有

\[\gcd \left(\operatorname{lcm}_{j \not = i} \{a_j\} , a_i \right) <a_i \]

但是显然处理不了这么大的数。
容易发现将 \(\gcd\) 放到 \(\operatorname{lcm}\) 里面是一样的效果,这样就只用考虑 \(a_i\) 的因子了,运算中的数一定不会超过 \(a_i\)

#include<bits/stdc++.h>
#define fo(i,a,b) for(int i=a;i<=b;++i)
#define fd(i,a,b) for(int i=a;i>=b;--i)
using namespace std;
typedef long long ll;
const int N=110;
int n;
ll a[N],b[N];
bool bz[N];
int main(){
	scanf("%d",&n);
	fo(i,1,n)scanf("%lld",&a[i]);
	fd(i,n,1){
		int t=0;
		fo(j,1,n)if(!bz[j]){
			ll v=1;
			fo(k,1,n)if(!bz[k] && k!=j){
				ll u=__gcd(a[j],a[k]);
				v=v/__gcd(u,v)*u;
			}
			if(v<a[j]){t=j;break;}
		}
		if(!t){
			puts("No");
			return 0;
		}
		b[i]=a[t];
		bz[t]=1;
	}
	puts("Yes");
	fo(i,1,n)printf("%lld ",b[i]);
	printf("\n");

	return 0;
}
posted @ 2022-11-15 21:29  Kelvin2005  阅读(19)  评论(0编辑  收藏  举报