57 typedef typename ResGraphType::Edge ResGraphEdge; |
57 typedef typename ResGraphType::Edge ResGraphEdge; |
58 |
58 |
59 class ModLengthMap { |
59 class ModLengthMap { |
60 //typedef typename ResGraphType::template NodeMap<Length> NodeMap; |
60 //typedef typename ResGraphType::template NodeMap<Length> NodeMap; |
61 typedef typename Graph::template NodeMap<Length> NodeMap; |
61 typedef typename Graph::template NodeMap<Length> NodeMap; |
62 const ResGraphType& G; |
62 const ResGraphType& res_graph; |
63 // const EdgeIntMap& rev; |
63 // const EdgeIntMap& rev; |
64 const LengthMap &ol; |
64 const LengthMap &ol; |
65 const NodeMap &pot; |
65 const NodeMap &pot; |
66 public : |
66 public : |
67 typedef typename LengthMap::KeyType KeyType; |
67 typedef typename LengthMap::KeyType KeyType; |
68 typedef typename LengthMap::ValueType ValueType; |
68 typedef typename LengthMap::ValueType ValueType; |
69 |
69 |
70 ValueType operator[](typename ResGraphType::Edge e) const { |
70 ValueType operator[](typename ResGraphType::Edge e) const { |
71 if (G.forward(e)) |
71 if (res_graph.forward(e)) |
72 return ol[e]-(pot[G.head(e)]-pot[G.tail(e)]); |
72 return ol[e]-(pot[res_graph.head(e)]-pot[res_graph.tail(e)]); |
73 else |
73 else |
74 return -ol[e]-(pot[G.head(e)]-pot[G.tail(e)]); |
74 return -ol[e]-(pot[res_graph.head(e)]-pot[res_graph.tail(e)]); |
75 } |
75 } |
76 |
76 |
77 ModLengthMap(const ResGraphType& _G, |
77 ModLengthMap(const ResGraphType& _res_graph, |
78 const LengthMap &o, const NodeMap &p) : |
78 const LengthMap &o, const NodeMap &p) : |
79 G(_G), /*rev(_rev),*/ ol(o), pot(p){}; |
79 res_graph(_res_graph), /*rev(_rev),*/ ol(o), pot(p){}; |
80 };//ModLengthMap |
80 };//ModLengthMap |
81 |
81 |
82 |
82 |
83 protected: |
83 protected: |
84 |
84 |
85 //Input |
85 //Input |
86 const Graph& G; |
86 const Graph& graph; |
87 const LengthMap& length; |
87 const LengthMap& length; |
88 const SupplyDemandMap& supply_demand;//supply or demand of nodes |
88 const SupplyDemandMap& supply_demand;//supply or demand of nodes |
89 |
89 |
90 |
90 |
91 //auxiliary variables |
91 //auxiliary variables |
102 |
102 |
103 |
103 |
104 public : |
104 public : |
105 |
105 |
106 |
106 |
107 MinCostFlow(Graph& _G, LengthMap& _length, SupplyDemandMap& _supply_demand) : G(_G), |
107 MinCostFlow(Graph& _graph, LengthMap& _length, SupplyDemandMap& _supply_demand) : graph(_graph), |
108 length(_length), supply_demand(_supply_demand), flow(_G), potential(_G){ } |
108 length(_length), supply_demand(_supply_demand), flow(_graph), potential(_graph){ } |
109 |
109 |
110 |
110 |
111 ///Runs the algorithm. |
111 ///Runs the algorithm. |
112 |
112 |
113 ///Runs the algorithm. |
113 ///Runs the algorithm. |
114 |
114 |
115 ///\todo May be it does make sense to be able to start with a nonzero |
115 ///\todo May be it does make sense to be able to start with a nonzero |
116 /// feasible primal-dual solution pair as well. |
116 /// feasible primal-dual solution pair as well. |
117 int run() { |
117 void run() { |
118 |
118 |
119 //Resetting variables from previous runs |
119 //Resetting variables from previous runs |
120 //total_length = 0; |
120 //total_length = 0; |
121 |
121 |
122 typedef typename Graph::template NodeMap<int> HeapMap; |
122 typedef typename Graph::template NodeMap<int> HeapMap; |
123 typedef Heap< Node, SupplyDemand, typename Graph::template NodeMap<int>, |
123 typedef Heap< Node, SupplyDemand, typename Graph::template NodeMap<int>, |
124 std::greater<SupplyDemand> > HeapType; |
124 std::greater<SupplyDemand> > HeapType; |
125 |
125 |
126 //A heap for the excess nodes |
126 //A heap for the excess nodes |
127 HeapMap excess_nodes_map(G,-1); |
127 HeapMap excess_nodes_map(graph,-1); |
128 HeapType excess_nodes(excess_nodes_map); |
128 HeapType excess_nodes(excess_nodes_map); |
129 |
129 |
130 //A heap for the deficit nodes |
130 //A heap for the deficit nodes |
131 HeapMap deficit_nodes_map(G,-1); |
131 HeapMap deficit_nodes_map(graph,-1); |
132 HeapType deficit_nodes(deficit_nodes_map); |
132 HeapType deficit_nodes(deficit_nodes_map); |
133 |
133 |
134 //A container to store nonabundant arcs |
134 //A container to store nonabundant arcs |
135 list<Edge> nonabundant_arcs; |
135 list<Edge> nonabundant_arcs; |
136 |
136 |
137 FOR_EACH_LOC(typename Graph::EdgeIt, e, G){ |
137 |
|
138 FOR_EACH_LOC(typename Graph::EdgeIt, e, graph){ |
138 flow.set(e,0); |
139 flow.set(e,0); |
139 nonabundant_arcs.push_back(e); |
140 nonabundant_arcs.push_back(e); |
140 } |
141 } |
141 |
142 |
142 //Initial value for delta |
143 //Initial value for delta |
143 SupplyDemand delta = 0; |
144 SupplyDemand delta = 0; |
144 |
145 |
145 typedef UnionFindEnum<Node, Graph::template NodeMap> UFE; |
146 typedef UnionFindEnum<Node, Graph::template NodeMap> UFE; |
146 |
147 |
147 //A union-find structure to store the abundant components |
148 //A union-find structure to store the abundant components |
148 UFE::MapType abund_comp_map(G); |
149 UFE::MapType abund_comp_map(graph); |
149 UFE abundant_components(abund_comp_map); |
150 UFE abundant_components(abund_comp_map); |
150 |
151 |
151 |
152 |
152 |
153 |
153 FOR_EACH_LOC(typename Graph::NodeIt, n, G){ |
154 FOR_EACH_LOC(typename Graph::NodeIt, n, graph){ |
154 excess_deficit.set(n,supply_demand[n]); |
155 excess_deficit.set(n,supply_demand[n]); |
155 //A supply node |
156 //A supply node |
156 if (excess_deficit[n] > 0){ |
157 if (excess_deficit[n] > 0){ |
157 excess_nodes.push(n,excess_deficit[n]); |
158 excess_nodes.push(n,excess_deficit[n]); |
158 } |
159 } |
172 |
173 |
173 //It'll be allright as an initial value, though this value |
174 //It'll be allright as an initial value, though this value |
174 //can be the maximum deficit here |
175 //can be the maximum deficit here |
175 SupplyDemand max_excess = delta; |
176 SupplyDemand max_excess = delta; |
176 |
177 |
|
178 //ConstMap<Edge,SupplyDemand> ConstEdgeMap; |
|
179 |
177 //We need a residual graph which is uncapacitated |
180 //We need a residual graph which is uncapacitated |
178 ResGraphType res_graph(G, flow); |
181 ResGraphType res_graph(graph, flow); |
179 |
182 |
180 |
183 //An EdgeMap to tell which arcs are abundant |
|
184 template typename Graph::EdgeMap<bool> abundant_arcs(graph); |
|
185 |
|
186 //Let's construct the sugraph consisting only of the abundant edges |
|
187 typedef ConstMap< typename Graph::Node, bool > ConstNodeMap; |
|
188 ConstNodeMap const_true_map(true); |
|
189 typedef SubGraphWrapper< Graph, ConstNodeMap, |
|
190 template typename Graph::EdgeMap<bool> > |
|
191 AbundantGraph; |
|
192 AbundantGraph abundant_graph(graph, const_true_map, abundant_arcs ); |
|
193 |
|
194 //Let's construct the residual graph for the abundant graph |
|
195 typedef ResGraphWrapper<const AbundantGraph,int,CapacityMap,EdgeIntMap> |
|
196 ResAbGraph; |
|
197 //Again uncapacitated |
|
198 ResAbGraph res_ab_graph(abundant_graph, flow); |
|
199 |
|
200 //We need things for the bfs |
|
201 typename ResAbGraph::NodeMap<bool> bfs_reached(res_ab_graph); |
|
202 typename ResAbGraph::NodeMap<typename ResAbGraph::Edge> |
|
203 bfs_pred(res_ab_graph); |
|
204 NullMap<typename ResAbGraph::Node, int> bfs_dist_dummy(res_ab_graph); |
|
205 //We want to run bfs-es (more) on this graph 'res_ab_graph' |
|
206 Bfs < ResAbGraph , |
|
207 typename ResAbGraph::NodeMap<bool>, |
|
208 typename ResAbGraph::NodeMap<typename ResAbGraph::Edge>, |
|
209 NullMap<typename ResAbGraph::Node, int> > |
|
210 bfs(res_ab_graph, bfs_reached, bfs_pred, bfs_dist_dummy); |
181 |
211 |
182 ModLengthMap mod_length(res_graph, length, potential); |
212 ModLengthMap mod_length(res_graph, length, potential); |
183 |
213 |
184 Dijkstra<ResGraphType, ModLengthMap> dijkstra(res_graph, mod_length); |
214 Dijkstra<ResGraphType, ModLengthMap> dijkstra(res_graph, mod_length); |
185 |
215 |
203 if (flow[i]>=buf){ |
233 if (flow[i]>=buf){ |
204 Node a = abundant_components.find(res_graph.head(i)); |
234 Node a = abundant_components.find(res_graph.head(i)); |
205 Node b = abundant_components.find(res_graph.tail(i)); |
235 Node b = abundant_components.find(res_graph.tail(i)); |
206 //Merge |
236 //Merge |
207 if (a != b){ |
237 if (a != b){ |
208 //Find path and augment |
|
209 //!!! |
|
210 //Find path and augment |
|
211 abundant_components.join(a,b); |
238 abundant_components.join(a,b); |
|
239 //We want to push the smaller |
|
240 //Which has greater absolut value excess/deficit |
|
241 Node root=(abs(excess_deficit[a])>abs(excess_deficit[b]))?a:b; |
|
242 //Which is the other |
|
243 Node non_root = ( a == root ) ? b : a ; |
|
244 abundant_components.makeRep(root); |
|
245 SupplyDemand qty_to_augment = abs(excess_deficit[non_root]); |
|
246 //Push the positive value |
|
247 if (excess_deficit[non_root] < 0) |
|
248 swap(root, non_root); |
|
249 //If the non_root node has excess/deficit at all |
|
250 if (qty_to_augment>0){ |
|
251 //Find path and augment |
|
252 bfs.run(non_root); |
|
253 //root should be reached |
|
254 |
|
255 //Augmenting on the found path |
|
256 Node n=root; |
|
257 ResGraphEdge e; |
|
258 while (n!=non_root){ |
|
259 e = bfs_pred(n); |
|
260 n = res_graph.tail(e); |
|
261 res_graph.augment(e,qty_to_augment); |
|
262 } |
|
263 |
|
264 //We know that non_root had positive excess |
|
265 excess_nodes[non_root] -= qty_to_augment; |
|
266 //But what about root node |
|
267 //It might have been positive and so became larger |
|
268 if (excess_deficit[root]>0){ |
|
269 excess_nodes[root] += qty_to_augment; |
|
270 } |
|
271 else{ |
|
272 //Or negative but not turned into positive |
|
273 deficit_nodes[root] -= qty_to_augment; |
|
274 } |
|
275 |
|
276 //Update the excess_deficit map |
|
277 excess_deficit[non_root] -= qty_to_augment; |
|
278 excess_deficit[root] += qty_to_augment; |
|
279 |
|
280 |
|
281 } |
212 } |
282 } |
213 //What happens to i? |
283 //What happens to i? |
214 nonabundant_arcs.erase(i); |
284 //Marci and Zsolt says I shouldn't do such things |
|
285 nonabundant_arcs.erase(i++); |
|
286 abundant_arcs[i] = true; |
215 } |
287 } |
216 else |
288 else |
217 ++i; |
289 ++i; |
218 } |
290 } |
219 } |
291 } |
220 |
292 |
221 |
293 |
222 Node s = excess_nodes.top(); |
294 Node s = excess_nodes.top(); |
223 SupplyDemand max_excess = excess_nodes[s]; |
295 SupplyDemand max_excess = excess_nodes[s]; |
224 Node t = deficit_nodes.top(); |
296 Node t = deficit_nodes.top(); |
225 if (max_excess < dificit_nodes[t]){ |
297 if (max_excess < deficit_nodes[t]){ |
226 max_excess = dificit_nodes[t]; |
298 max_excess = deficit_nodes[t]; |
227 } |
299 } |
228 |
300 |
229 |
301 |
230 while(max_excess > 0){ |
302 while(max_excess > (n-1)*delta/n){ |
231 |
303 |
232 |
304 |
233 //s es t valasztasa |
305 //s es t valasztasa |
234 |
306 |
235 //Dijkstra part |
307 //Dijkstra part |
236 dijkstra.run(s); |
308 dijkstra.run(s); |
237 |
309 |
238 /*We know from theory that t can be reached |
310 /*We know from theory that t can be reached |
239 if (!dijkstra.reached(t)){ |
311 if (!dijkstra.reached(t)){ |
240 //There are no k paths from s to t |
312 //There are no k paths from s to t |
241 break; |
313 break; |
242 }; |
314 }; |