题解 CF1401C 【Mere Array】

这题是一道小思维题,放在 C 的话难度还是比较低的。

我看有些题解只给了做法没有给证明,所以来说一下。

题意是说如果两个数最大公约数是序列最小值就可以交换。问最小交换次数使得单调不下降。

先给结论:我们先对 \(a\) 数组排序,得到最终数列。考虑每个数,如果这个数不等于最终数列的数并且不能被数列最小值整除,那么输出 NO。否则遍历完后输出 YES

为什么呢?可以先考虑如果一个数不能被数列最小值整除,那么它肯定无法做任何交换,那么如果还不等于最终数列的数,那肯定是不行的。

如果这个数就等于最终数列的数,保留即可。

如果这个数可以整除数列最小值,那么对于两个满足此条件的数(设为 \(x\)\(y\)),可以和最小值 \(z\) 进行如下操作:

x y z
x z y
z x y
y x z

可以发现,最小值的位置没有改变,而 \(x\)\(y\) 的位置进行了交换。所以对于所有这样的数,两两可以交换(间接交换)。那么肯定可以达到目标。

其实如果这两个数里有一个数是最小值,那么直接交换即可。依旧是满足的。

所以结论成立。

#include<bits/stdc++.h>
using namespace std;
int a[100001],b[100001]; 
int main()
{
	int t;
	cin >> t;
	while (t--)
	{
		int n;
		cin >> n;
		for (int i=1;i<=n;i++) 
		{
			cin >> a[i];
			b[i]=a[i];
		}
		sort(b+1,b+n+1);
		for (int i=1;i<=n;i++) 
		{
			if (a[i]!=b[i]&&a[i]%b[1]!=0)
			{
				cout << "NO" << endl;
				goto no;
			}
		}
		cout << "YES" << endl;
		no:;
	}
    return 0;
}
posted @ 2020-10-24 20:03  Little09  阅读(112)  评论(0)    收藏  举报