1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119
| #include<cstdio> #include<algorithm> #define fo(i,a,b) for(int i=a;i<=b;i++) #define fd(i,a,b) for(int i=a;i>=b;i--) using namespace std;
const int maxn=5e5+5;
int n,K,ans;
int tot,go[maxn],next[maxn],f1[maxn],fa[maxn]; void ins(int x,int y) { go[++tot]=y; next[tot]=f1[x]; f1[x]=tot; }
int d[maxn],com[maxn]; bool roll[maxn]; void topo() { int j=0; fo(i,1,n) if (!com[i]) d[++j]=i; for(int i=1; i<=j; i++) { if (--com[fa[d[i]]]==0) d[++j]=fa[d[i]]; } fo(i,1,n) if (com[i]) roll[i]=1; }
int tim[maxn]; bool bz[maxn]; void dfs(int k) { bz[k]=1; tim[k]=K+500; for(int p=f1[k]; p; p=next[p]) { dfs(go[p]); tim[k]=min(tim[k],tim[go[p]]+1); } if (k==1) tim[k]=0; else if (tim[k]>K && !roll[k]) { tim[k]=1; ans++; } }
int ga[2*maxn],stp[2*maxn]; int get(int x) { if (ga[x]==x) return x; int t=ga[x]; ga[x]=get(ga[x]); stp[x]+=stp[t]; return ga[x]; }
int c0,c[2*maxn],f[2*maxn]; void calc(int x) { c[c0=1]=x; for(int i=fa[x]; i!=x; i=fa[i]) c[++c0]=i; fo(i,1,c0) c[c0+i]=c[i]; fo(i,1,c0) dfs(c[i]); fo(i,1,2*c0) tim[c[i]]=min(tim[c[i]],tim[c[i-1]]+1); fo(i,1,2*c0) ga[i]=i, stp[i]=0; fd(i,2*c0,2*c0-K+1) f[i]=2*c0+1; int last=2*c0+1; fd(i,2*c0,K+1) { if (tim[c[i]]>K) last=i; f[i-K]=last; } int nmin=n+500; fo(i,1,c0) if (tim[c[i]]>K) { int ans1=0, last=0; for(int j=i; j && j-i+1<=c0; j=f[j]) { int t2=get(j); ans1+=1+stp[j]; if (last) { int t1=get(last); ga[t1]=t2; stp[t1]+=stp[j]+1; } j=t2; last=j; } nmin=min(nmin,ans1); } ans+=(nmin==n+500) ?0 :nmin ; }
int main() { scanf("%d %d",&n,&K); fo(i,1,n) { int x,y; scanf("%d %d",&x,&y); fa[x]=y; com[y]++; } topo(); fo(i,1,n) if (!roll[i]) ins(fa[i],i); fo(i,1,n) if (roll[i] && !bz[i]) calc(i); printf("%d\n",ans); }
|