Advertisement
Guest User

Untitled

a guest
Jan 28th, 2020
78
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 2.22 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <algorithm>
  4.  
  5. #define forn(i, n) for(int i = 1; i <= n; ++i)
  6. #define MAX 1001
  7.  
  8. using namespace std;
  9.  
  10. vector<vector<int>>graph(MAX);
  11. vector<vector<int>>reversed(MAX);
  12.  
  13. struct Edge {
  14. int from;
  15. int to;
  16. };
  17.  
  18. vector <Edge> edges;
  19.  
  20. bool mark[MAX];
  21. int components[MAX];
  22.  
  23. vector <int> oto;
  24.  
  25. int n, m, counter; //counter - для подсчета компонент, чтобы вывести количество ребер, просто прибавим единицу...
  26.  
  27. void dfs_s(int v) {
  28. mark[v] = 1;
  29. for( int x : graph[v]) {
  30. if (mark[x] == 0)
  31. dfs_s(x);
  32. }
  33. oto.push_back(v);
  34. }
  35.  
  36. void dfs_r(int v) { //DFS по обратным ребрам
  37. if (components[v]) return ;
  38. components[v] = counter; //пометили вершинку из компоненты, аналог массива mark[MAX]
  39. for (int x : reversed[v]) {
  40. dfs_r(x);
  41. }
  42. }
  43.  
  44. void top_sort() {
  45. forn(i, n)
  46. mark[i] = 0;
  47. oto.clear();
  48. forn(i, n)
  49. if(!mark[i])
  50. dfs_s(i);
  51. reverse(oto.begin(), oto.end());
  52. //for (int i: oto)
  53. // cout << i << " ";
  54. return;
  55. }
  56.  
  57. int components_coloring() {
  58. counter = 0;
  59. for (int a = 1; a <= n; a++)
  60. if (!components[a]) {
  61. counter++;
  62. dfs_r(a);
  63. }
  64. return counter;
  65. }
  66.  
  67.  
  68. int main() {
  69. ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
  70.  
  71. cin >> n >> m;
  72. int u, v;
  73.  
  74. counter = 0; //счетчик компонент сильной связности
  75. int ce = 0; //счетчик ребер в конденсации
  76.  
  77. forn(i, m) { //считали граф
  78. cin >> v >> u;
  79. graph[v].push_back(u);
  80. edges.push_back({v, u});
  81. }
  82.  
  83. forn(i, n) { //перевернули граф, чтобы проходиться по обратным ребрам
  84. for (int x : graph[i])
  85. reversed[i].push_back(x);
  86. }
  87.  
  88. top_sort(); //топологическая сортировка
  89. components_coloring();
  90.  
  91. for(auto x : edges) {
  92. if (components[x.from] == components[x.to])
  93. ce++;
  94. }
  95. cout << ce << "\n";
  96. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement