CF2031B
提供一个比较好想的思路。
读题发现给定的序列是一个排列,即任意两个数互不相同。考虑 \(n\) 这个数,它只能与 \(n-1\) 交换,因此它要么在第 \(n\) 个位置上,要么在第 \(n-1\) 个位置上,且在后者情况下必须满足 \(p_n=n-1\) 才能有解。将 \(n\) 固定下来后,\(n-1\) 只能与 \(n-2\) 交换了,和上一步十分相似,以此类推即可。
单组数据时间复杂度 \(O(n)\),代码十分简洁。
#include <iostream>
#include <cstdio>
#define int long long
using namespace std;
int n,a[1000001],p[1000001],flag;
void solve( void )
{
cin >> n;
for( int i = 1 ; i <= n ; i ++ )
{
cin >> a[i];
p[a[i]] = i;
}
flag = 0;
for( int i = n ; i > 1 ; i -- )
{
if( p[i] == i ) continue;//已经出现在了正确的位置上
else if( p[i] == i - 1 && p[i - 1] == i )//交换一次
{
swap( p[i] , p[i - 1] );
continue;
}
flag = 1;//无解
break;
}
if( !flag ) cout << "YES\n";
else cout << "NO\n";
return;
}
signed main()
{
ios::sync_with_stdio( false );
cin.tie( 0 );
cout.tie( 0 );
int T;
cin >> T;
while( T -- )
solve();
return 0;
}

浙公网安备 33010602011771号