版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/wwwlps/article/details/88679980
题目大意: 给定一个1~n的排列,和m对可以交换的组合(有顺序,1 2的话表示在前面的1可以和相邻的2交换位置,而如果2在前面则不能),问变换之后最后一个数通过可以最大前移多少位。
题目解答:
嗯......我们先想一下,从后往前看,如果离p[n]最近的满足交换的数是否应该优先换到p[n]的前面(如果可以的话)呢?你想一下,如果前面一个位置下标为i的数换到了位置下标为i+q的地方,i和i+q之间的数的相对顺序是不会改变的,这对p[n]来说也是没有影响的,这个有点类似于冒泡,所以我们与其先和离p[n]较远的数交换,不如先换近的。
代码:
#include <iostream>
#include <set>
#include <vector>
#include <algorithm>
#include <cstring>
using namespace std;
const int maxn=300005;
const int maxz=500005;
int p[maxn];
int book[maxn];
int n,m;
vector<int>v[maxn];
int main()
{
ios::sync_with_stdio(false);
cin>>n>>m;
for(int i=0;i<n;i++)
{
cin>>p[i];
}
for(int i=0;i<m;i++)
{
int x,y;
cin>>x>>y;
v[x].push_back(y);
}
int nowp=n-1;
book[p[n-1]]=1;
int ans=0;
for(int i=n-2;i>=0;i--)
{
int e=p[i];
int cnt=0;
for(int j=0;j<v[e].size();j++)
{
int u=v[e][j];
if(book[u])
{
cnt++;
}
}
if(cnt+i==n-1-ans)
ans++;
else
book[e]=1;
}
cout << ans << endl;
return 0;
}
map<int,bool>mmp[maxn]也可以用来存储键值对是否存在,这里用的vector