where n is the number of nodes in the graph, and m the number of edges in it. Note that the call to EGalgPRminSTcut produces a maximum pre_flow, to obtain a flow you should call the EGalgPRmaxSTflow that takes the graph produced by EGalgPRminSTcut and convert the preflow into a real flow. We also choose to use to register the number of nodes with distance labels
where n is the number of nodes in the network. This is done because whenever the number of nodes with distance labels k is zero, then all nodes with distance labels above k can be set to n (and thus be added to the partially computed cut-set). This is an (inportant) empirical speed-up, but does not affect the worst case complexity analysis. It is important to note that this algorithm (as implemented here) WILL FAIL if an edge has infinite capacities. To handle that case either we must re-program it, or you can put capacities suficiently large on them (for example 2 times the sum of all bounded capacities) for this algorithm to work.
This implementation does use global relabeling, namelly, the strategy when once in a while (for example every n or m relabeling operations) we recompute the exact distance labels. The use of this heuristic (together with the gap heuristic) have been reported to be the most successfull in practice (see "On Implementing Push-Relabel Method For The Maximum FLow Problem" from Boris V. Cherkassy and Andrew V. Goldberg.) and also in the test that we have performed on the fractional solutions of TSP's instances from the TSPLIB set of problems using CONCORDE.
Files | |
| file | eg_push_relabel.c |
| file | eg_push_relabel.ex.c |
| file | eg_push_relabel.h |
Data Structures | |
| struct | EGalgPRedge_t |
| Edge Structure needed to run Push-Relabel algorithm on a network. More... | |
| struct | EGalgPRgraph_t |
| Graph structure needed to run Push-Relabel algorithm (with highest label node selection rule). More... | |
| struct | EGalgPRnode_t |
| Node structure neede to run Push-Relabel algorithm on a network. More... | |
| struct | EGalgPRse_t |
| capacitated edge structure with forward/backward information. More... | |
| #define | EGalgPRprofile |
| If profiling is enable (i.e. __PR_PROFILE__ <= DEBUG), print some profiling information of the min s-t cut used up to now, and reset all internal counters to zero, if profiling is not enabled, nothing happen. | |
Defines | |
| #define | __PR_DEBUGL__ 100 |
| Level of debugging in the code. | |
| #define | __PR_PROFILE__ 100 |
| Level of profiling in the code. | |
| #define | __PR_TEST_VERBOSE__ 100 |
| Level of debugging in the code. | |
| #define | __PR_VERBOSE__ 100 |
| Level of debugging in the code. | |
| #define | EG_PR_RELABEL 1 |
| If set to non-zero, use the global relabeling heuristic (to be called every n number of relabel operations performed. if set to zero, it won't use this heuristic. Note thought that it has been shown that this is a very efficient heuristic to reduce the total running time, specially in the EGalgPRminSTcut function call. | |
| #define | EG_PR_RELABEL_FREC 1U |
| If EG_PR_RELABEL is set to one, then this initeger controls how often we perform the global relabeling heuristic (in multiples of number of nodes), the default value is 1. | |
| #define | EGalgPRedgeClear(edge_pt) |
| clear a pointer to an EGalgPRedge_t structure, and let it ready to be freed if necesary. | |
| #define | EGalgPRedgeInit(edge_pt) |
| Initialize a pointer to an EGalgPRedge_t structure. | |
| #define | EGalgPRedgeReset(edge_pt) |
| Reset the given edge pointer (as if it were new). | |
| #define | EGalgPRgraphClear(graph_pt) EGeDgraphClear(&((graph_pt)->G)) |
| clear a pointer to an EGalgPRgraph_t structure, and let it ready to be freed if necesary. | |
| #define | EGalgPRgraphInit(graph_pt) EGeDgraphInit(&((graph_pt)->G)) |
| Initialize a pointer to an EGalgPRgraph_t structure. | |
| #define | EGalgPRgraphReset(graph_pt) EGeDgraphReset(&((graph_pt)->G)) |
| Reset the given graph pointer (as if it were new). | |
| #define | EGalgPRnodeClear(node_pt) |
| clear a pointer to an EGalgPRnode_t structure, and let it ready to be freed if necesary. | |
| #define | EGalgPRnodeInit(node_pt) |
| Initialize a pointer to an EGalgPRnode_t structure. | |
| #define | EGalgPRnodeReset(node_pt) EGeDgraphNodeReset(&((node_pt)->v)) |
| Reset the given node pointer (as if it were new). | |
| #define | UPDATE(counter) |
| If using profiling, we count the number of push, relabels, nodes moved to S because we have a hole in the numb array, the number of levels that we we looked at, and the number of nodes that we move to the S cut because their label become bigger than number of nodes. | |
Typedefs | |
| typedef EGalgPRedge_t | EGalgPRedge_t |
| Edge Structure needed to run Push-Relabel algorithm on a network. | |
| typedef EGalgPRgraph_t | EGalgPRgraph_t |
| Graph structure needed to run Push-Relabel algorithm (with highest label node selection rule). | |
| typedef EGalgPRnode_t | EGalgPRnode_t |
| Node structure neede to run Push-Relabel algorithm on a network. | |
| typedef EGalgPRse_t | EGalgPRse_t |
| capacitated edge structure with forward/backward information. | |
Functions | |
| static int | EGalgPRcomputeLabels (EGalgPRgraph_t *const G, EGalgPRnode_t *const t, unsigned int *const numb, EGeList_t *DIST) |
| Compute the exact label distance in the graph to the given node. | |
| static int | EGalgPRglobalRelabel (EGalgPRgraph_t *const G, EGalgPRnode_t *const s, EGalgPRnode_t *const t, unsigned int const n_nodes, unsigned int *const numb, EGeList_t *const LEVEL, EGeList_t *const DIST) |
| Re-compute the global distance labels. | |
| int | EGalgPRmaxSTflow (EGalgPRgraph_t *const G, EGalgPRnode_t *const s, EGalgPRnode_t *const t) |
Compute a maximum flow from the ouput produced by EGalgPRminCur. | |
| int | EGalgPRminSTcut (EGalgPRgraph_t *const G, EGalgPRnode_t *const s, EGalgPRnode_t *const t) |
Compute a minimum cut. | |
| static int | EGalgPRnumb (const unsigned int hole, const unsigned int max_numb, const unsigned int n_nodes, unsigned int *const numb, EGeList_t *const DIST) |
| Once we have found a 'hole' in the numb arrray, all nodes with distance labels above the given value, can be set to the number of nodes in the network (and thus be assumed to be in the S cut). | |
| int | EGalgPRoptimalityTest (EGalgPRgraph_t *const G, EGalgPRnode_t *const s, EGalgPRnode_t *const t, EGlpNum_t *error) |
Check if the given input graph (with it's residual capacities) represent an optimal solution to the maximum flow / minimum capacity cut. | |
| static int | EGalgPRpreprocess (EGalgPRgraph_t *const G, EGalgPRnode_t *const s, EGalgPRnode_t *const t, unsigned int *const numb, EGeList_t *const LEVEL, EGeList_t *const DIST) |
| Initialize flow to zero, and saturate forward edges in the source. | |
| static int | EGalgPRpush (EGalgPRse_t *const edge_pt, EGlpNum_t flow, EGeList_t *const LEVEL, const unsigned int n_nodes) |
| Perform a push operation in an edge. | |
| static int | EGalgPRpushRelabel (EGalgPRnode_t *const node_pt, unsigned int *const numb, const unsigned int n_nodes, EGeList_t *const LEVEL, EGeList_t *const DIST) |
| Push/Relabel the given node. | |
| int | main (int argc, char **argv) |
| example of usage of the Preflow-Push algorithm as implemented in (EGalgPushRelabel). | |
| static void | pr_usage (char **argv) |
| display usage of this program | |
Variables | |
| static unsigned long long | __last_global = 0 |
| counter to keep track of the relabel operations performed, this is needed to implement the global relabeling heuristic | |
|
|
Level of debugging in the code.
Definition at line 86 of file eg_push_relabel.h. |
|
|
Level of profiling in the code.
Definition at line 98 of file eg_push_relabel.h. |
|
|
Level of debugging in the code.
Definition at line 90 of file eg_push_relabel.h. |
|
|
Level of debugging in the code.
Definition at line 94 of file eg_push_relabel.h. |
|
|
If set to non-zero, use the global relabeling heuristic (to be called every n number of relabel operations performed. if set to zero, it won't use this heuristic. Note thought that it has been shown that this is a very efficient heuristic to reduce the total running time, specially in the EGalgPRminSTcut function call.
Definition at line 129 of file eg_push_relabel.h. |
|
|
If EG_PR_RELABEL is set to one, then this initeger controls how often we perform the global relabeling heuristic (in multiples of number of nodes), the default value is 1.
Definition at line 135 of file eg_push_relabel.h. |
|
|
Value: ({\
EGlpNumClearVar((edge_pt)->fw.r);\
EGlpNumClearVar((edge_pt)->fw.u);\
EGlpNumClearVar((edge_pt)->bw.r);\
EGlpNumClearVar((edge_pt)->bw.u);\
EGeDgraphEdgeClear(&((edge_pt)->fw.e));\
EGeDgraphEdgeClear(&((edge_pt)->bw.e));})
Definition at line 251 of file eg_push_relabel.h. |
|
|
Value: ({\
EGalgPRedge_t*const __EGalgPR_ie = (edge_pt);\
EGlpNumInitVar(__EGalgPR_ie->fw.r);\
EGlpNumInitVar(__EGalgPR_ie->fw.u);\
EGlpNumInitVar(__EGalgPR_ie->bw.r);\
EGlpNumInitVar(__EGalgPR_ie->bw.u);\
EGeDgraphEdgeInit(&(__EGalgPR_ie->fw.e));\
EGeDgraphEdgeInit(&(__EGalgPR_ie->bw.e));\
__EGalgPR_ie->bw.type = 1;\
__EGalgPR_ie->fw.type = 0;})
Definition at line 223 of file eg_push_relabel.h. |
|
|
Value: ({\
EGalgPRedge_t*const __EGalgPR_ie = (edge_pt);\
EGeDgraphEdgeReset(&(__EGalgPR_ie->fw.e));\
EGeDgraphEdgeReset(&(__EGalgPR_ie->bw.e));\
__EGalgPR_ie->bw.type = 1;\
__EGalgPR_ie->fw.type = 0;})
Definition at line 240 of file eg_push_relabel.h. |
|
|
clear a pointer to an EGalgPRgraph_t structure, and let it ready to be freed if necesary.
Definition at line 284 of file eg_push_relabel.h. |
|
|
Initialize a pointer to an EGalgPRgraph_t structure.
Definition at line 271 of file eg_push_relabel.h. |
|
|
Reset the given graph pointer (as if it were new).
Definition at line 279 of file eg_push_relabel.h. |
|
|
Value: ({\
EGlpNumClearVar((node_pt)->e);\
EGeDgraphNodeClear(&((node_pt)->v));})
Definition at line 184 of file eg_push_relabel.h. |
|
|
Value: ({\
EGalgPRnode_t*const __EGalgPR_in = (node_pt);\
EGlpNumInitVar(__EGalgPR_in->e);\
EGeDgraphNodeInit(&(__EGalgPR_in->v));})
Definition at line 168 of file eg_push_relabel.h. |
|
|
Reset the given node pointer (as if it were new).
Definition at line 179 of file eg_push_relabel.h. |
|
|
If profiling is enable (i.e. __PR_PROFILE__ <= DEBUG), print some profiling information of the min s-t cut used up to now, and reset all internal counters to zero, if profiling is not enabled, nothing happen.
Definition at line 120 of file eg_push_relabel.h. |
|
|
If using profiling, we count the number of push, relabels, nodes moved to S because we have a hole in the numb array, the number of levels that we we looked at, and the number of nodes that we move to the S cut because their label become bigger than number of nodes.
Definition at line 41 of file eg_push_relabel.c. |
|
|
Edge Structure needed to run Push-Relabel algorithm on a network.
|
|
|
Graph structure needed to run Push-Relabel algorithm (with highest label node selection rule).
|
|
|
Node structure neede to run Push-Relabel algorithm on a network.
|
|
|
capacitated edge structure with forward/backward information.
|
|
||||||||||||||||||||
|
Compute the exact label distance in the graph to the given node.
Definition at line 67 of file eg_push_relabel.c. |
|
||||||||||||||||||||||||||||||||
|
Re-compute the global distance labels.
Definition at line 486 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||||||
|
Compute a maximum
Definition at line 652 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||||||
|
Compute a minimum
Definition at line 550 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||||||||||||||
|
Once we have found a 'hole' in the numb arrray, all nodes with distance labels above the given value, can be set to the number of nodes in the network (and thus be assumed to be in the S cut).
Definition at line 430 of file eg_push_relabel.c. |
|
||||||||||||||||||||
|
Check if the given input graph (with it's residual capacities) represent an optimal solution to the maximum
Definition at line 721 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||||||||||||||||||
|
Initialize flow to zero, and saturate forward edges in the source.
Definition at line 225 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||||||||||
|
Perform a push operation in an edge.
Definition at line 170 of file eg_push_relabel.c. |
|
||||||||||||||||||||||||
|
Push/Relabel the given node.
Definition at line 303 of file eg_push_relabel.c. Here is the call graph for this function: ![]() |
|
||||||||||||
|
example of usage of the Preflow-Push algorithm as implemented in (EGalgPushRelabel). We read a file from the input whose two first numbers are the number of nodes and edges (we assume that the graph is undirected ), and then a 3-tupla with head tail capacity. we use the last field (capacity) as the capacity of the algorithm, and compute the shortest path from node 0 to node 1. Definition at line 42 of file eg_push_relabel.ex.c. Here is the call graph for this function: ![]() |
|
|
display usage of this program
Definition at line 29 of file eg_push_relabel.ex.c. |
|
|
counter to keep track of the relabel operations performed, this is needed to implement the global relabeling heuristic
Definition at line 48 of file eg_push_relabel.c. |
1.4.5