alpar@1
|
1 |
/* ASSIGN, Assignment Problem */
|
alpar@1
|
2 |
|
alpar@1
|
3 |
/* Written in GNU MathProg by Andrew Makhorin <mao@gnu.org> */
|
alpar@1
|
4 |
|
alpar@1
|
5 |
/* The assignment problem is one of the fundamental combinatorial
|
alpar@1
|
6 |
optimization problems.
|
alpar@1
|
7 |
|
alpar@1
|
8 |
In its most general form, the problem is as follows:
|
alpar@1
|
9 |
|
alpar@1
|
10 |
There are a number of agents and a number of tasks. Any agent can be
|
alpar@1
|
11 |
assigned to perform any task, incurring some cost that may vary
|
alpar@1
|
12 |
depending on the agent-task assignment. It is required to perform all
|
alpar@1
|
13 |
tasks by assigning exactly one agent to each task in such a way that
|
alpar@1
|
14 |
the total cost of the assignment is minimized.
|
alpar@1
|
15 |
|
alpar@1
|
16 |
(From Wikipedia, the free encyclopedia.) */
|
alpar@1
|
17 |
|
alpar@1
|
18 |
param m, integer, > 0;
|
alpar@1
|
19 |
/* number of agents */
|
alpar@1
|
20 |
|
alpar@1
|
21 |
param n, integer, > 0;
|
alpar@1
|
22 |
/* number of tasks */
|
alpar@1
|
23 |
|
alpar@1
|
24 |
set I := 1..m;
|
alpar@1
|
25 |
/* set of agents */
|
alpar@1
|
26 |
|
alpar@1
|
27 |
set J := 1..n;
|
alpar@1
|
28 |
/* set of tasks */
|
alpar@1
|
29 |
|
alpar@1
|
30 |
param c{i in I, j in J}, >= 0;
|
alpar@1
|
31 |
/* cost of allocating task j to agent i */
|
alpar@1
|
32 |
|
alpar@1
|
33 |
var x{i in I, j in J}, >= 0;
|
alpar@1
|
34 |
/* x[i,j] = 1 means task j is assigned to agent i
|
alpar@1
|
35 |
note that variables x[i,j] are binary, however, there is no need to
|
alpar@1
|
36 |
declare them so due to the totally unimodular constraint matrix */
|
alpar@1
|
37 |
|
alpar@1
|
38 |
s.t. phi{i in I}: sum{j in J} x[i,j] <= 1;
|
alpar@1
|
39 |
/* each agent can perform at most one task */
|
alpar@1
|
40 |
|
alpar@1
|
41 |
s.t. psi{j in J}: sum{i in I} x[i,j] = 1;
|
alpar@1
|
42 |
/* each task must be assigned exactly to one agent */
|
alpar@1
|
43 |
|
alpar@1
|
44 |
minimize obj: sum{i in I, j in J} c[i,j] * x[i,j];
|
alpar@1
|
45 |
/* the objective is to find a cheapest assignment */
|
alpar@1
|
46 |
|
alpar@1
|
47 |
solve;
|
alpar@1
|
48 |
|
alpar@1
|
49 |
printf "\n";
|
alpar@1
|
50 |
printf "Agent Task Cost\n";
|
alpar@1
|
51 |
printf{i in I} "%5d %5d %10g\n", i, sum{j in J} j * x[i,j],
|
alpar@1
|
52 |
sum{j in J} c[i,j] * x[i,j];
|
alpar@1
|
53 |
printf "----------------------\n";
|
alpar@1
|
54 |
printf " Total: %10g\n", sum{i in I, j in J} c[i,j] * x[i,j];
|
alpar@1
|
55 |
printf "\n";
|
alpar@1
|
56 |
|
alpar@1
|
57 |
data;
|
alpar@1
|
58 |
|
alpar@1
|
59 |
/* These data correspond to an example from [Christofides]. */
|
alpar@1
|
60 |
|
alpar@1
|
61 |
/* Optimal solution is 76 */
|
alpar@1
|
62 |
|
alpar@1
|
63 |
param m := 8;
|
alpar@1
|
64 |
|
alpar@1
|
65 |
param n := 8;
|
alpar@1
|
66 |
|
alpar@1
|
67 |
param c : 1 2 3 4 5 6 7 8 :=
|
alpar@1
|
68 |
1 13 21 20 12 8 26 22 11
|
alpar@1
|
69 |
2 12 36 25 41 40 11 4 8
|
alpar@1
|
70 |
3 35 32 13 36 26 21 13 37
|
alpar@1
|
71 |
4 34 54 7 8 12 22 11 40
|
alpar@1
|
72 |
5 21 6 45 18 24 34 12 48
|
alpar@1
|
73 |
6 42 19 39 15 14 16 28 46
|
alpar@1
|
74 |
7 16 34 38 3 34 40 22 24
|
alpar@1
|
75 |
8 26 20 5 17 45 31 37 43 ;
|
alpar@1
|
76 |
|
alpar@1
|
77 |
end;
|