原题链接在这里:Problem - D - Codeforces
然后这题不是二分图,因为二分图会有两个明确的集合,而且这个数据跑二分图很明显会挂,
其实这题就是一个很简单的匹配,因为是内部自己匹配,而且是单向的,所以直接构造就行了,而且就算后面有换的情况,也是从这个匹配换成了另一个匹配,对匹配总数不会造成影响。
然后这题!测试数据t很大,如果每次在while(t--)里面memset整个数组的话时间会爆炸,这点要吸取教训
看了土豆的代码,发现vector是一个好东西,貌似可以直接像数组一样访问其中的元素。
1 #include "bits/stdc++.h" 2 using namespace std; 3 const int MAX=2e5+5; 4 int t,n,a[MAX]; 5 int ff[MAX],fa[MAX],zt[MAX]; 6 inline int read(){ 7 int an=0,x=1;char c=getchar(); 8 while (c<'0' || c>'9') {if (c=='-') x=-1;c=getchar();} 9 while (c>='0' && c<='9') {an=an*10+c-'0';c=getchar();} 10 return an*x; 11 } 12 int main(){ 13 freopen ("d.in","r",stdin); 14 freopen ("d.out","w",stdout); 15 int i,j,zz,tt,ans; 16 t=read();//scanf("%d",&t); 17 while (t--){ 18 n=read();//scanf("%d",&n); 19 for (i=1;i<=n;i++){ 20 a[i]=read();//scanf("%d",a+i); 21 fa[i]=ff[i]=-1; 22 } 23 ans=0; 24 for (i=1;i<=n;i++) 25 if (fa[a[i]]==-1){ 26 fa[a[i]]=i; 27 ff[i]=a[i]; 28 ans++; 29 } 30 //for (i=1;i<=n;i++) cout<<ff[i]<<' ';cout<<endl; 31 zt[0]=0; 32 for (i=n;i>=1;i--) 33 if (fa[i]==-1) 34 zt[++zt[0]]=i; 35 tt=0; 36 if (zt[0]==0) goto away; 37 for (i=1;i<=n;i++) 38 if (ff[i]==-1){ 39 //zt=q.top();q.pop(); 40 //cout<<i<<' '<<zt<<endl; 41 zz=zt[++tt]; 42 if (zz!=i) ff[i]=zz; 43 else{ 44 ff[i]=a[i]; 45 ff[fa[a[i]]]=zz; 46 fa[zz]=fa[a[i]]; 47 fa[a[i]]=i; 48 } 49 } 50 away: printf("%d ",ans); 51 for (i=1;i<=n;i++) printf("%d ",ff[i]);printf(" "); 52 } 53 return 0; 54 }