[关闭]
@lychee123 2017-09-27T18:36:34.000000Z 字数 1493 阅读 963

PowerOJ 1683 费用流

图论 费用流

PowerOJ 1683 费用流

从起点到终点,求两条边不相交的路径,使得总长度最短。输出最短的总长度

  1. #include<bits/stdc++.h>
  2. using namespace std;
  3. const int maxn = 2e3 + 5;
  4. const int maxm = 1e5 + 5;
  5. struct EDGE
  6. {
  7. int to, next, flow, cost;
  8. EDGE() {}
  9. EDGE(int to, int next, int flow, int cost) : to(to), next(next), flow(flow), cost(cost) {}
  10. } edge[maxm];
  11. int head[maxn], edgecnt, maxNodeNum;
  12. void init()
  13. {
  14. memset(head, -1, sizeof(head));
  15. edgecnt = 0;
  16. maxNodeNum = 0;
  17. }
  18. void AddEdge(int st, int en, int flow, int cost)
  19. {
  20. edge[edgecnt] = EDGE(en, head[st], flow, cost);
  21. head[st] = edgecnt++;
  22. edge[edgecnt] = EDGE(st, head[en], 0, -cost);
  23. head[en] = edgecnt++;
  24. maxNodeNum = max(maxNodeNum, max(st, en));
  25. }
  26. int pre[maxn], dis[maxn];
  27. bool SPFA(int st, int en)
  28. {
  29. static bool vis[maxn];
  30. memset(dis, 0x7F, sizeof(int) * (maxNodeNum + 1));
  31. dis[st] = 0;
  32. queue<int> q;
  33. q.push(st);
  34. while (!q.empty())
  35. {
  36. int u = q.front();
  37. q.pop();
  38. vis[u] = 0;
  39. for (int i = head[u]; ~i; i = edge[i].next)
  40. {
  41. int v = edge[i].to;
  42. if (edge[i].flow && dis[v] > dis[u] + edge[i].cost)
  43. {
  44. if (!vis[v])
  45. {
  46. vis[v] = true;
  47. q.push(v);
  48. }
  49. dis[v] = dis[u] + edge[i].cost;
  50. pre[v] = i;
  51. }
  52. }
  53. }
  54. return dis[en] != 0x7F7F7F7F;
  55. }
  56. pair<int, int> solve(int st, int en, int maxFlow = INT_MAX)
  57. {
  58. int cost = 0, flow = 0;
  59. while (SPFA(st, en))
  60. {
  61. int d = maxFlow - flow;
  62. for (int u = en; u != st; u = edge[pre[u] ^ 1].to)
  63. d = min(d, edge[pre[u]].flow);
  64. flow += d;
  65. for (int u = en; u != st; u = edge[pre[u] ^ 1].to)
  66. {
  67. edge[pre[u]].flow -= d;
  68. edge[pre[u] ^ 1].flow += d;
  69. cost += edge[pre[u]].cost * d;
  70. }
  71. if (flow == maxFlow) break;
  72. }
  73. return make_pair(cost, flow);
  74. }
  75. int main()
  76. {
  77. int n, m;
  78. while (~scanf("%d %d", &n, &m))
  79. {
  80. init();
  81. while (m--)
  82. {
  83. int f, t, j;
  84. scanf("%d %d %d", &f, &t, &j);
  85. AddEdge(f, t, 1, j);
  86. AddEdge(t, f, 1, j);
  87. }
  88. AddEdge(0, 1, 2, 0);
  89. printf("%d\n", solve(0, n).first);
  90. }
  91. return 0;
  92. }
添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注