forked from xiongwq16/cplex-java-api-tutorial-zh
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathMIPex4.java
More file actions
202 lines (177 loc) · 6.82 KB
/
MIPex4.java
File metadata and controls
202 lines (177 loc) · 6.82 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
package examples;
/* --------------------------------------------------------------------------
* File: MIPex4.java
* Version 12.9.0
* --------------------------------------------------------------------------
* Licensed Materials - Property of IBM
* 5725-A06 5725-A29 5724-Y48 5724-Y49 5724-Y54 5724-Y55 5655-Y21
* Copyright IBM Corporation 2007, 2019. All Rights Reserved.
*
* US Government Users Restricted Rights - Use, duplication or
* disclosure restricted by GSA ADP Schedule Contract with
* IBM Corp.
* --------------------------------------------------------------------------
*
* MIPex4.java - Reading in and optimizing a problem using a callback
* to log or interrupt or an IloCplex.Aborter to interrupt
*
* To run this example, command line arguments are required.
* i.e., MIPex4 filename option
* where option is one of
* t to use the time-limit-gap callback
* l to use the logging callback
* a to use the aborter
*
* Example:
* java MIPex4 mexample.mps l
*/
import ilog.concert.*;
import ilog.cplex.*;
public class MIPex4 {
static void usage() {
System.out.println("usage: MIPex4 <filename> <option>");
System.out.println(" t to use the time-limit-gap callback");
System.out.println(" l to use the logging callback");
System.out.println(" a to use the aborter");
}
// Spend at least timeLimit seconds on optimization, but once
// this limit is reached, quit as soon as the solution is acceptable
static class TimeLimitCallback extends IloCplex.MIPInfoCallback {
IloCplex _cplex;
boolean _aborted;
double _timeLimit;
double _timeStart;
double _acceptableGap;
TimeLimitCallback(IloCplex cplex, boolean aborted, double timeStart,
double timeLimit, double acceptableGap) {
_cplex = cplex;
_aborted = aborted;
_timeStart = timeStart;
_timeLimit = timeLimit;
_acceptableGap = acceptableGap;
}
public void main() throws IloException {
if ( !_aborted && hasIncumbent() ) {
double gap = 100.0 * getMIPRelativeGap();
double timeUsed = _cplex.getCplexTime() - _timeStart;
if ( timeUsed > _timeLimit && gap < _acceptableGap ) {
System.out.println("");
System.out.println("Good enough solution at "
+ timeUsed + " sec., gap = "
+ gap + "%, quitting.");
_aborted = true;
abort();
}
}
}
}
// Log new incumbents if they are at better than the old by a
// relative tolerance of 1e-5; also log progress info every
// 100 nodes.
static class LogCallback extends IloCplex.MIPInfoCallback {
IloNumVar[] _var;
long _lastLog;
double _lastIncumbent;
LogCallback(IloNumVar[] var, int lastLog, double lastIncumbent) {
_var = var;
_lastLog = lastLog;
_lastIncumbent = lastIncumbent;
}
public void main() throws IloException {
boolean newIncumbent = false;
long nodes = getNnodes64();
if ( hasIncumbent() &&
Math.abs(_lastIncumbent - getIncumbentObjValue())
> 1e-5*(1.0 + Math.abs(getIncumbentObjValue())) ) {
_lastIncumbent = getIncumbentObjValue();
newIncumbent = true;
}
if ( nodes >= _lastLog + 100 || newIncumbent ) {
if ( !newIncumbent ) _lastLog = nodes;
System.out.print("Nodes = " + nodes
+ "(" + getNremainingNodes64() + ")"
+ " Best objective = " + getBestObjValue());
if ( hasIncumbent() ) {
System.out.println (" Incumbent objective = " +
getIncumbentObjValue());
}
else {
System.out.println("");
}
}
if ( newIncumbent ) {
System.out.println("New incumbent values: ");
int n = _var.length;
double[] x = getIncumbentValues(_var, 0, n);
for (int j = 0; j < n; j++) {
System.out.println("Variable " + j + ": Value = " + x[j]);
}
}
}
}
public static void main(String[] args) {
if ( args.length != 2 ) {
usage();
return;
}
try {
boolean useLoggingCallback = false;
boolean useTimeLimitCallback = false;
boolean useAborter = false;
IloCplex.Aborter myAborter;
IloCplex cplex = new IloCplex();
switch ( args[1].charAt(0) ) {
case 't':
useTimeLimitCallback = true;
break;
case 'l':
useLoggingCallback = true;
break;
case 'a':
useAborter = true;
break;
default:
usage();
return;
}
cplex.importModel(args[0]);
IloLPMatrix lp = (IloLPMatrix)cplex.LPMatrixIterator().next();
IloObjective obj = cplex.getObjective();
if ( useLoggingCallback ) {
// Set an overall node limit in case callback conditions
// are not met.
cplex.setParam(IloCplex.Param.MIP.Limits.Nodes, 5000);
double lastObjVal =
(obj.getSense() == IloObjectiveSense.Minimize ) ?
Double.MAX_VALUE : -Double.MAX_VALUE;
cplex.use(new LogCallback(lp.getNumVars(), -100000, lastObjVal));
// Turn off CPLEX logging
cplex.setParam(IloCplex.Param.MIP.Display, 0);
}
else if ( useTimeLimitCallback ) {
cplex.use(new TimeLimitCallback(cplex, false, cplex.getCplexTime(), 1.0, 10.0));
}
else if ( useAborter ) {
myAborter = new IloCplex.Aborter();
cplex.use(myAborter);
// Typically, you would pass the Aborter object to
// another thread or pass it to an interrupt handler,
// and monitor for some event to occur. When it does,
// call the Aborter's abort method.
//
// To illustrate its use without creating a thread or
// an interrupt handler, abort immediately by calling
// abort before the solve.
//
myAborter.abort();
}
cplex.solve();
System.out.println("Solution status = " + cplex.getStatus());
System.out.println("CPLEX status = " + cplex.getCplexStatus());
cplex.end();
}
catch (IloException e) {
System.err.println("Concert exception caught: " + e);
}
}
}