Processing math: 100%
My Algorithm : kopricky アルゴリズムライブラリ

kopricky アルゴリズムライブラリ

Minimum Cost Flow Algorithm

コードについての説明(個人的メモ)

(すべての辺の容量および流すフローの流量が非負整数の場合における)最小費用流を求めるアルゴリズム.

(関数)
solve(s,t,f) : s から t へ流量 f 流すのにかかる最小費用

時間計算量: O(|F|mlogn) (流量を |F| とする)

コード

  1. template<typename CapType, typename CostType> class MinCostFlow {
  2. public:
  3. using Cat = CapType;
  4. using Cot = CostType;
  5. using pti = pair<Cot, int>;
  6. struct edge {
  7. int to; Cat cap; Cot cost; int rev;
  8. };
  9. const int V;
  10. const Cot inf;
  11. vector<vector<edge> > G;
  12. vector<Cot> h, dist;
  13. vector<int> prevv, preve;
  14. MinCostFlow(int node_size) : V(node_size), inf(numeric_limits<Cot>::max()),
  15. G(V), h(V, 0), dist(V), prevv(V), preve(V){}
  16. void add_edge(int from, int to, Cat cap, Cot cost){
  17. G[from].push_back((edge){to, cap, cost, (int)G[to].size()});
  18. G[to].push_back((edge){from, 0, -cost, (int)G[from].size() - 1});
  19. }
  20. Cot solve(int s, int t, Cat f){
  21. Cot res = 0;
  22. while(f > 0){
  23. priority_queue<pti,vector<pti>,greater<pti> > que;
  24. fill(dist.begin(), dist.end(), inf);
  25. dist[s] = 0;
  26. que.push(pti(0, s));
  27. while(!que.empty()){
  28. pti p = que.top();
  29. que.pop();
  30. int v = p.second;
  31. if(dist[v] < p.first) continue;
  32. for(int i = 0; i < (int)G[v].size(); i++){
  33. edge& e = G[v][i];
  34. if(e.cap > 0 && dist[e.to] > dist[v] + e.cost + h[v] - h[e.to]){
  35. dist[e.to] = dist[v] + e.cost + h[v] - h[e.to];
  36. prevv[e.to] = v, preve[e.to] = i;
  37. que.push(pti(dist[e.to], e.to));
  38. }
  39. }
  40. }
  41. if(dist[t] == inf) return -1;
  42. for(int i = 0; i < V; i++){
  43. if(dist[i] != inf) h[i] += dist[i];
  44. }
  45. Cat d = f;
  46. for(int v = t; v != s; v = prevv[v]){
  47. d = min(d, G[prevv[v]][preve[v]].cap);
  48. }
  49. f -= d;
  50. res += h[t] * d;
  51. for(int v = t; v != s; v = prevv[v]){
  52. edge& e = G[prevv[v]][preve[v]];
  53. e.cap -= d;
  54. G[v][e.rev].cap += d;
  55. }
  56. }
  57. return res;
  58. }
  59. };

verify 用の問題

AOJ : Minimum Cost Flow 提出コード