牛客网NC276110题解:小红的数组重排
牛客网NC276110题解:小红的数组重排
题目解析
算法思路
- 对数组进行排序(非降序)
- 检查特殊情况:
- 如果存在三个连续相等的元素,则无解
- 如果前两个元素都是0,则无解
- 若不存在特殊情况,则排序后的数组即为所求
为什么这样做是正确的?
当我们对数组排序后,相邻元素的乘积往往会递增。但有两种特殊情况需要排除:
- 三个连续相等的数:假设有三个连续相等的数x,那么会出现x×x = x×x,不满足严格递增
- 开头两个0:如果前两个元素都是0,则a₁×a₂ = 0,而后续任何包含0的乘积也为0,无法形成严格递增序列
代码实现
#include <bits/stdc++.h>
using namespace std;
int main()
{int n;cin>>n;int k[n];for(int i=0;i<n;i++){cin>>k[i];}sort(k,k+n);//数组从小到大排列。for(int i=0;i<n-2;i++){if(k[i]==k[i+1]&&k[i+1]==k[i+2]){cout<<"NO";return 0;}}if(k[0]==k[1]&&k[0]==0){cout<<"NO";return 0;}cout<<"YES"<<endl;for(int i=0;i<n;i++){cout<<k[i]<<" ";}return 0;
}
复杂度分析
- 时间复杂度:O(nlogn),主要来自排序操作
- 空间复杂度:O(n),存储输入数组
示例分析
以示例1为例:[7, 2, 5, 1]
- 排序后:
[1, 2, 5, 7]
- 检查特殊情况:
- 无三个连续相等的数
- 开头两个数不都是0
- 输出排序后的数组:
1 2 5 7
验证:1×2 < 2×5 < 5×7,即 2 < 10 < 35 ✓
注意题目示例输出了1 5 2 7
,这也是正确答案的一种,因为:1×5 < 5×2 < 2×7,即 5 < 10 < 14 ✓
总结
这道题的关键是发现排序后的数组通常能满足要求,只需排除特殊情况。解题思路简洁明了,实现也很高效。