这道题的意思是给你一个有向图边的信息, 求出最少需要几条边就可以使这个图的拓扑图唯一, 二分答案然后check一下就行了, 代码如下:
#include <bits/stdc++.h> using namespace std; struct edge{ int u, v, id; }; vector<edge> e; vector<int> G[100000 + 100]; int indeg[100000 + 100]; int n, m; bool check(int mid){ memset(indeg, 0, sizeof(indeg)); for(int i=0; i<=mid; i++) indeg[e[i].v]++; queue<int> que; for(int i=1; i<=n; i++) if(indeg[i] == 0) que.push(i); if(que.size() > 1) return false; int tp ; while(!que.empty()) { int u = que.front(); que.pop(); tp = 0; for(int i=0; i<G[u].size(); i++) if(e[G[u][i]].id<=mid) { //printf("%d %d %d ", e[G[u][i]].u, e[G[u][i]].v, e[G[u][i]].id); int v = e[G[u][i]].v; indeg[v]--; if(indeg[v] == 0){ que.push(v); tp++; } } if(tp > 1) return false; } return true; } int main() { scanf("%d%d", &n, &m); for(int i=0; i<m; i++) { int u, v; scanf("%d%d", &u, &v); e.push_back((edge){u, v, i}); G[u].push_back(e.size()-1); } int res = -2; int l=0, r=m-1; while(l <= r){ int mid = (l+r)/2; if(check(mid)){ res = mid; r = mid - 1; } else l = mid + 1; } printf("%d ", res+1); return 0; }