Loading docs/graph/chord.md +101 −89 Original line number Diff line number Diff line Loading @@ -151,17 +151,24 @@ 参考代码: ```cpp while(cur) { p[cur]=h[nww];rnk[p[cur]]=cur; h[nww]=nxt[h[nww]];lst[h[nww]]=0; lst[p[cur]]=nxt[p[cur]]=0;tf[p[cur]]=true; for(vector<int>::iterator it=G[p[cur]].begin();it!=G[p[cur]].end();it++)if(!tf[*it]) { while (cur) { p[cur] = h[nww]; rnk[p[cur]] = cur; h[nww] = nxt[h[nww]]; lst[h[nww]] = 0; lst[p[cur]] = nxt[p[cur]] = 0; tf[p[cur]] = true; for (vector<int>::iterator it = G[p[cur]].begin(); it != G[p[cur]].end(); it++) if (!tf[*it]) { if (h[deg[*it]] == *it) h[deg[*it]] = nxt[*it]; nxt[lst[*it]]=nxt[*it];lst[nxt[*it]]=lst[*it]; lst[*it]=nxt[*it]=0;deg[*it]++; nxt[*it]=h[deg[*it]];lst[h[deg[*it]]]=*it;h[deg[*it]]=*it; nxt[lst[*it]] = nxt[*it]; lst[nxt[*it]] = lst[*it]; lst[*it] = nxt[*it] = 0; deg[*it]++; nxt[*it] = h[deg[*it]]; lst[h[deg[*it]]] = *it; h[deg[*it]] = *it; } cur--; if (h[nww + 1]) nww++; Loading @@ -183,18 +190,23 @@ while(cur) ```cpp jud = true; for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { cur = 0; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)if(rnk[p[i]]<rnk[*it]) { for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) if (rnk[p[i]] < rnk[*it]) { s[++cur] = *it; if (rnk[s[cur]] < rnk[s[1]]) swap(s[1], s[cur]); } for(int j=2;j<=cur;j++)if(!st[s[1]].count(s[j])){jud=false;break;} for (int j = 2; j <= cur; j++) if (!st[s[1]].count(s[j])) { jud = false; break; } } if(!jud)printf("Imperfect\n"); else printf("Perfect\n"); if (!jud) printf("Imperfect\n"); else printf("Perfect\n"); ``` 至此, **弦图判定问题** 可以在 $O(n+m)$ 的时间复杂度内解决。 Loading @@ -216,18 +228,17 @@ $A\subsetneqq B$ 当且仅当 $|A|+1\le |B|$ 。 问题转化为判断是否存在 $y$ ,满足 $nxt_y=x$ 且 $|N(x)|+1\le |N(y)|$ 。时间复杂度 $O(n+m)$ 。 ```cpp for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { cur = 0; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)if(rnk[p[i]]<rnk[*it]) { for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) if (rnk[p[i]] < rnk[*it]) { s[++cur] = *it; if (rnk[s[cur]] < rnk[s[1]]) swap(s[1], s[cur]); } fst[p[i]]=s[1];N[p[i]]=cur; fst[p[i]] = s[1]; N[p[i]] = cur; } for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { if (!vis[p[i]]) ans++; if (N[p[i]] >= N[fst[p[i]]] + 1) vis[fst[p[i]]] = true; } Loading @@ -254,10 +265,11 @@ for(int i=1;i<=n;i++)ans=max(ans,deg[i]+1); 正确性证明:设以上方案独立集数和团覆盖数为 $t$ ,由定义得 $t\le \alpha(G),t\ge \kappa(G)$ ,由 **Lemma 2** 得, $\alpha(G)\le \kappa(G)$ ,所以 $t=\alpha(G)=\kappa(G)$ 。 ```cpp for(int i=1;i<=n;i++)if(!vis[p[i]]) { for (int i = 1; i <= n; i++) if (!vis[p[i]]) { ans++; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)vis[*it]=true; for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) vis[*it] = true; } ``` Loading Loading
docs/graph/chord.md +101 −89 Original line number Diff line number Diff line Loading @@ -151,17 +151,24 @@ 参考代码: ```cpp while(cur) { p[cur]=h[nww];rnk[p[cur]]=cur; h[nww]=nxt[h[nww]];lst[h[nww]]=0; lst[p[cur]]=nxt[p[cur]]=0;tf[p[cur]]=true; for(vector<int>::iterator it=G[p[cur]].begin();it!=G[p[cur]].end();it++)if(!tf[*it]) { while (cur) { p[cur] = h[nww]; rnk[p[cur]] = cur; h[nww] = nxt[h[nww]]; lst[h[nww]] = 0; lst[p[cur]] = nxt[p[cur]] = 0; tf[p[cur]] = true; for (vector<int>::iterator it = G[p[cur]].begin(); it != G[p[cur]].end(); it++) if (!tf[*it]) { if (h[deg[*it]] == *it) h[deg[*it]] = nxt[*it]; nxt[lst[*it]]=nxt[*it];lst[nxt[*it]]=lst[*it]; lst[*it]=nxt[*it]=0;deg[*it]++; nxt[*it]=h[deg[*it]];lst[h[deg[*it]]]=*it;h[deg[*it]]=*it; nxt[lst[*it]] = nxt[*it]; lst[nxt[*it]] = lst[*it]; lst[*it] = nxt[*it] = 0; deg[*it]++; nxt[*it] = h[deg[*it]]; lst[h[deg[*it]]] = *it; h[deg[*it]] = *it; } cur--; if (h[nww + 1]) nww++; Loading @@ -183,18 +190,23 @@ while(cur) ```cpp jud = true; for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { cur = 0; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)if(rnk[p[i]]<rnk[*it]) { for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) if (rnk[p[i]] < rnk[*it]) { s[++cur] = *it; if (rnk[s[cur]] < rnk[s[1]]) swap(s[1], s[cur]); } for(int j=2;j<=cur;j++)if(!st[s[1]].count(s[j])){jud=false;break;} for (int j = 2; j <= cur; j++) if (!st[s[1]].count(s[j])) { jud = false; break; } } if(!jud)printf("Imperfect\n"); else printf("Perfect\n"); if (!jud) printf("Imperfect\n"); else printf("Perfect\n"); ``` 至此, **弦图判定问题** 可以在 $O(n+m)$ 的时间复杂度内解决。 Loading @@ -216,18 +228,17 @@ $A\subsetneqq B$ 当且仅当 $|A|+1\le |B|$ 。 问题转化为判断是否存在 $y$ ,满足 $nxt_y=x$ 且 $|N(x)|+1\le |N(y)|$ 。时间复杂度 $O(n+m)$ 。 ```cpp for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { cur = 0; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)if(rnk[p[i]]<rnk[*it]) { for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) if (rnk[p[i]] < rnk[*it]) { s[++cur] = *it; if (rnk[s[cur]] < rnk[s[1]]) swap(s[1], s[cur]); } fst[p[i]]=s[1];N[p[i]]=cur; fst[p[i]] = s[1]; N[p[i]] = cur; } for(int i=1;i<=n;i++) { for (int i = 1; i <= n; i++) { if (!vis[p[i]]) ans++; if (N[p[i]] >= N[fst[p[i]]] + 1) vis[fst[p[i]]] = true; } Loading @@ -254,10 +265,11 @@ for(int i=1;i<=n;i++)ans=max(ans,deg[i]+1); 正确性证明:设以上方案独立集数和团覆盖数为 $t$ ,由定义得 $t\le \alpha(G),t\ge \kappa(G)$ ,由 **Lemma 2** 得, $\alpha(G)\le \kappa(G)$ ,所以 $t=\alpha(G)=\kappa(G)$ 。 ```cpp for(int i=1;i<=n;i++)if(!vis[p[i]]) { for (int i = 1; i <= n; i++) if (!vis[p[i]]) { ans++; for(vector<int>::iterator it=G[p[i]].begin();it!=G[p[i]].end();it++)vis[*it]=true; for (vector<int>::iterator it = G[p[i]].begin(); it != G[p[i]].end(); it++) vis[*it] = true; } ``` Loading