1 | // Copyright (C) 2002, International Business Machines |
---|
2 | // Corporation and others. All Rights Reserved. |
---|
3 | |
---|
4 | |
---|
5 | // The point of this example is to show how to create a model without |
---|
6 | // using mps files. |
---|
7 | |
---|
8 | // This reads a network problem created by netgen which can be |
---|
9 | // downloaded from www.netlib.org/lp/generators/netgen |
---|
10 | // This is a generator due to Darwin Klingman |
---|
11 | |
---|
12 | #include "ClpSimplex.hpp" |
---|
13 | #include "ClpFactorization.hpp" |
---|
14 | #include "ClpNetworkMatrix.hpp" |
---|
15 | #include <stdio.h> |
---|
16 | #include <assert.h> |
---|
17 | #include <cmath> |
---|
18 | |
---|
19 | int main (int argc, const char *argv[]) |
---|
20 | { |
---|
21 | int numberColumns; |
---|
22 | int numberRows; |
---|
23 | |
---|
24 | FILE * fp; |
---|
25 | if ( argc>1 ) { |
---|
26 | fp = fopen(argv[1],"r"); |
---|
27 | if (!fp) { |
---|
28 | fprintf(stderr,"Unable to open file %s\n",argv[1]); |
---|
29 | exit(1); |
---|
30 | } |
---|
31 | } else { |
---|
32 | fp = fopen("input.130","r"); |
---|
33 | if (!fp) { |
---|
34 | fprintf(stderr,"Unable to open file input.l30 in Samples directory\n"); |
---|
35 | exit(1); |
---|
36 | } |
---|
37 | } |
---|
38 | int problem; |
---|
39 | char temp[100]; |
---|
40 | // read and skip |
---|
41 | fscanf(fp,"%s",temp); |
---|
42 | assert (!strcmp(temp,"BEGIN")); |
---|
43 | fscanf(fp,"%*s %*s %d %d %*s %*s %d %*s",&problem, &numberRows, |
---|
44 | &numberColumns); |
---|
45 | // scan down to SUPPLY |
---|
46 | while (fgets(temp,100,fp)) { |
---|
47 | if (!strncmp(temp,"SUPPLY",6)) |
---|
48 | break; |
---|
49 | } |
---|
50 | if (strncmp(temp,"SUPPLY",6)) { |
---|
51 | fprintf(stderr,"Unable to find SUPPLY\n"); |
---|
52 | exit(2); |
---|
53 | } |
---|
54 | // get space for rhs |
---|
55 | double * lower = new double[numberRows]; |
---|
56 | double * upper = new double[numberRows]; |
---|
57 | int i; |
---|
58 | for (i=0;i<numberRows;i++) { |
---|
59 | lower[i]=0.0; |
---|
60 | upper[i]=0.0; |
---|
61 | } |
---|
62 | // ***** Remember to convert to C notation |
---|
63 | while (fgets(temp,100,fp)) { |
---|
64 | int row; |
---|
65 | int value; |
---|
66 | if (!strncmp(temp,"ARCS",4)) |
---|
67 | break; |
---|
68 | sscanf(temp,"%d %d",&row,&value); |
---|
69 | upper[row-1]=-value; |
---|
70 | lower[row-1]=-value; |
---|
71 | } |
---|
72 | if (strncmp(temp,"ARCS",4)) { |
---|
73 | fprintf(stderr,"Unable to find ARCS\n"); |
---|
74 | exit(2); |
---|
75 | } |
---|
76 | // number of columns may be underestimate |
---|
77 | int * head = new int[2*numberColumns]; |
---|
78 | int * tail = new int[2*numberColumns]; |
---|
79 | int * ub = new int[2*numberColumns]; |
---|
80 | int * cost = new int[2*numberColumns]; |
---|
81 | // ***** Remember to convert to C notation |
---|
82 | numberColumns=0; |
---|
83 | while (fgets(temp,100,fp)) { |
---|
84 | int iHead; |
---|
85 | int iTail; |
---|
86 | int iUb; |
---|
87 | int iCost; |
---|
88 | if (!strncmp(temp,"DEMAND",6)) |
---|
89 | break; |
---|
90 | sscanf(temp,"%d %d %d %d",&iHead,&iTail,&iCost,&iUb); |
---|
91 | iHead--; |
---|
92 | iTail--; |
---|
93 | head[numberColumns]=iHead; |
---|
94 | tail[numberColumns]=iTail; |
---|
95 | ub[numberColumns]=iUb; |
---|
96 | cost[numberColumns]=iCost; |
---|
97 | numberColumns++; |
---|
98 | } |
---|
99 | if (strncmp(temp,"DEMAND",6)) { |
---|
100 | fprintf(stderr,"Unable to find DEMAND\n"); |
---|
101 | exit(2); |
---|
102 | } |
---|
103 | // ***** Remember to convert to C notation |
---|
104 | while (fgets(temp,100,fp)) { |
---|
105 | int row; |
---|
106 | int value; |
---|
107 | if (!strncmp(temp,"END",3)) |
---|
108 | break; |
---|
109 | sscanf(temp,"%d %d",&row,&value); |
---|
110 | upper[row-1]=value; |
---|
111 | lower[row-1]=value; |
---|
112 | } |
---|
113 | if (strncmp(temp,"END",3)) { |
---|
114 | fprintf(stderr,"Unable to find END\n"); |
---|
115 | exit(2); |
---|
116 | } |
---|
117 | printf("Problem %d has %d rows and %d columns\n",problem, |
---|
118 | numberRows,numberColumns); |
---|
119 | fclose(fp); |
---|
120 | ClpSimplex model; |
---|
121 | // now build model - we have rhs so build columns - two elements |
---|
122 | // per column |
---|
123 | |
---|
124 | double * objective =new double[numberColumns]; |
---|
125 | double * lowerColumn = new double[numberColumns]; |
---|
126 | double * upperColumn = new double[numberColumns]; |
---|
127 | |
---|
128 | double * element = new double [2*numberColumns]; |
---|
129 | int * start = new int[numberColumns+1]; |
---|
130 | int * row = new int[2*numberColumns]; |
---|
131 | start[numberColumns]=2*numberColumns; |
---|
132 | for (i=0;i<numberColumns;i++) { |
---|
133 | start[i]=2*i; |
---|
134 | element[2*i]=-1.0; |
---|
135 | element[2*i+1]=1.0; |
---|
136 | row[2*i]=head[i]; |
---|
137 | row[2*i+1]=tail[i]; |
---|
138 | lowerColumn[i]=0.0; |
---|
139 | upperColumn[i]=ub[i]; |
---|
140 | objective[i]=cost[i]; |
---|
141 | } |
---|
142 | // Create Packed Matrix |
---|
143 | CoinPackedMatrix matrix; |
---|
144 | int * lengths = NULL; |
---|
145 | matrix.assignMatrix(true,numberRows,numberColumns, |
---|
146 | 2*numberColumns,element,row,start,lengths); |
---|
147 | ClpNetworkMatrix network(matrix); |
---|
148 | // load model |
---|
149 | |
---|
150 | model.loadProblem(network, |
---|
151 | lowerColumn,upperColumn,objective, |
---|
152 | lower,upper); |
---|
153 | |
---|
154 | delete [] lower; |
---|
155 | delete [] upper; |
---|
156 | delete [] head; |
---|
157 | delete [] tail; |
---|
158 | delete [] ub; |
---|
159 | delete [] cost; |
---|
160 | delete [] objective; |
---|
161 | delete [] lowerColumn; |
---|
162 | delete [] upperColumn; |
---|
163 | delete [] element; |
---|
164 | delete [] start; |
---|
165 | delete [] row; |
---|
166 | |
---|
167 | /* The confusing flow below is in to exercise both dual and primal |
---|
168 | when ClpNetworkMatrix storage used. |
---|
169 | |
---|
170 | For practical use just one call e.g. model.dual(); would be used. |
---|
171 | |
---|
172 | If network then factorization scheme is changed |
---|
173 | to be much faster. |
---|
174 | |
---|
175 | Still not as fast as a real network code, but more flexible |
---|
176 | */ |
---|
177 | model.factorization()->maximumPivots(200+model.numberRows()/100); |
---|
178 | model.factorization()->maximumPivots(1000); |
---|
179 | //model.factorization()->maximumPivots(1); |
---|
180 | if (model.numberRows()<50) |
---|
181 | model.messageHandler()->setLogLevel(63); |
---|
182 | model.dual(); |
---|
183 | model.setOptimizationDirection(-1); |
---|
184 | //model.messageHandler()->setLogLevel(63); |
---|
185 | model.primal(); |
---|
186 | model.setOptimizationDirection(1); |
---|
187 | model.primal(); |
---|
188 | return 0; |
---|
189 | } |
---|