2 * Based on: Jonker, R., & Volgenant, A. (1987). <i>A shortest augmenting path
3 * algorithm for dense and sparse linear assignment problems</i>. Computing,
7 #include "linear-assignment.h"
9 #define COST(column, row) cost[(column) + column_count * (row)]
12 * The parameter `cost` is the cost matrix: the cost to assign column j to row
13 * i is `cost[j + column_count * i].
15 void compute_assignment(int column_count, int row_count, int *cost,
16 int *column2row, int *row2column)
19 int *free_row, free_count = 0, saved_free_count, *pred, *col;
22 memset(column2row, -1, sizeof(int) * column_count);
23 memset(row2column, -1, sizeof(int) * row_count);
24 ALLOC_ARRAY(v, column_count);
26 /* column reduction */
27 for (j = column_count - 1; j >= 0; j--) {
30 for (i = 1; i < row_count; i++)
31 if (COST(j, i1) > COST(j, i))
34 if (row2column[i1] == -1) {
35 /* row i1 unassigned */
39 if (row2column[i1] >= 0)
40 row2column[i1] = -2 - row2column[i1];
45 /* reduction transfer */
46 ALLOC_ARRAY(free_row, row_count);
47 for (i = 0; i < row_count; i++) {
48 int j1 = row2column[i];
50 free_row[free_count++] = i;
52 row2column[i] = -2 - j1;
54 int min = COST(!j1, i) - v[!j1];
55 for (j = 1; j < column_count; j++)
56 if (j != j1 && min > COST(j, i) - v[j])
57 min = COST(j, i) - v[j];
63 (column_count < row_count ? row_count - column_count : 0)) {
69 /* augmenting row reduction */
70 for (phase = 0; phase < 2; phase++) {
73 saved_free_count = free_count;
75 while (k < saved_free_count) {
80 u1 = COST(j1, i) - v[j1];
83 for (j = 1; j < column_count; j++) {
84 int c = COST(j, i) - v[j];
114 free_row[free_count++] = i0;
122 saved_free_count = free_count;
123 ALLOC_ARRAY(d, column_count);
124 ALLOC_ARRAY(pred, column_count);
125 ALLOC_ARRAY(col, column_count);
126 for (free_count = 0; free_count < saved_free_count; free_count++) {
127 int i1 = free_row[free_count], low = 0, up = 0, last, k;
130 for (j = 0; j < column_count; j++) {
131 d[j] = COST(j, i1) - v[j];
140 for (k = up; k < column_count; k++) {
152 for (k = low; k < up; k++)
153 if (column2row[col[k]] == -1)
161 u1 = COST(j1, i) - v[j1] - min;
162 for (k = up; k < column_count; k++) {
164 c = COST(j, i) - v[j] - u1;
169 if (column2row[j] == -1)
180 /* updating of the column pieces */
181 for (k = 0; k < last; k++) {
183 v[j1] += d[j1] - min;
189 BUG("negative j: %d", j);
192 SWAP(j, row2column[i]);