@ohtaman/washi 0.2.0 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.ja.md +138 -122
- package/README.md +138 -122
- package/README.zh-CN.md +140 -124
- package/dist/browser/solvers/glpk.js +10 -2
- package/dist/browser/solvers/glpk.min.js +1 -1
- package/dist/browser/solvers/z3.js +34 -12
- package/dist/browser/solvers/z3.min.js +2 -2
- package/dist/browser/washi.js +562 -397
- package/dist/browser/washi.min.js +4 -4
- package/dist/lib/{constraint-XWdn0ID9.js → constraint-BRuB3ooC.js} +0 -3
- package/dist/lib/solvers/glpk.js +10 -2
- package/dist/lib/solvers/z3.js +35 -10
- package/dist/lib/washi.js +562 -412
- package/dist/types/index.d.ts +5 -7
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/modeler/constraint.d.ts +0 -3
- package/dist/types/modeler/constraint.d.ts.map +1 -1
- package/dist/types/modeler/expression.d.ts +23 -12
- package/dist/types/modeler/expression.d.ts.map +1 -1
- package/dist/types/modeler/index.d.ts +2 -4
- package/dist/types/modeler/index.d.ts.map +1 -1
- package/dist/types/modeler/model.d.ts +123 -40
- package/dist/types/modeler/model.d.ts.map +1 -1
- package/dist/types/modeler/parser.d.ts +9 -8
- package/dist/types/modeler/parser.d.ts.map +1 -1
- package/dist/types/modeler/quad-expr.d.ts +3 -1
- package/dist/types/modeler/quad-expr.d.ts.map +1 -1
- package/dist/types/modeler/solvers/glpk/solver.d.ts.map +1 -1
- package/dist/types/modeler/solvers/highs/solver.d.ts +1 -1
- package/dist/types/modeler/solvers/highs/solver.d.ts.map +1 -1
- package/dist/types/modeler/solvers/types.d.ts +1 -1
- package/dist/types/modeler/solvers/z3/loader.d.ts +12 -0
- package/dist/types/modeler/solvers/z3/loader.d.ts.map +1 -1
- package/dist/types/modeler/types.d.ts +8 -3
- package/dist/types/modeler/types.d.ts.map +1 -1
- package/dist/types/modeler/variable.d.ts +7 -6
- package/dist/types/modeler/variable.d.ts.map +1 -1
- package/package.json +11 -3
- package/dist/types/modeler/mip-compat.d.ts +0 -43
- package/dist/types/modeler/mip-compat.d.ts.map +0 -1
- package/dist/types/modeler/pulp-compat.d.ts +0 -67
- package/dist/types/modeler/pulp-compat.d.ts.map +0 -1
package/dist/browser/washi.js
CHANGED
|
@@ -1,32 +1,37 @@
|
|
|
1
1
|
import { a as e, c as t, i as n, l as r, n as i, o as a, r as o, s, t as c } from "./loader-CVt4CloI.js";
|
|
2
|
+
//#region src/modeler/types.ts
|
|
3
|
+
function l(e) {
|
|
4
|
+
return e && e.toLowerCase() === "maximize" ? "Maximize" : "Minimize";
|
|
5
|
+
}
|
|
6
|
+
//#endregion
|
|
2
7
|
//#region src/modeler/boolean-expr.ts
|
|
3
|
-
var
|
|
8
|
+
var u = 0, d = class {
|
|
4
9
|
and(e) {
|
|
5
|
-
return new
|
|
10
|
+
return new p("and", [this, e]);
|
|
6
11
|
}
|
|
7
12
|
or(e) {
|
|
8
|
-
return new
|
|
13
|
+
return new p("or", [this, e]);
|
|
9
14
|
}
|
|
10
15
|
implies(e) {
|
|
11
|
-
return new
|
|
16
|
+
return new p("implies", [this, e]);
|
|
12
17
|
}
|
|
13
18
|
xor(e) {
|
|
14
|
-
return new
|
|
19
|
+
return new p("xor", [this, e]);
|
|
15
20
|
}
|
|
16
21
|
not() {
|
|
17
|
-
return new
|
|
22
|
+
return new p("not", [this]);
|
|
18
23
|
}
|
|
19
|
-
},
|
|
24
|
+
}, f = class extends d {
|
|
20
25
|
id;
|
|
21
26
|
name;
|
|
22
27
|
value = null;
|
|
23
28
|
constructor(e) {
|
|
24
|
-
super(), this.id = ++
|
|
29
|
+
super(), this.id = ++u, this.name = e || `p_${this.id}`;
|
|
25
30
|
}
|
|
26
31
|
toString() {
|
|
27
32
|
return this.name;
|
|
28
33
|
}
|
|
29
|
-
},
|
|
34
|
+
}, p = class extends d {
|
|
30
35
|
op;
|
|
31
36
|
children;
|
|
32
37
|
constructor(e, t) {
|
|
@@ -36,27 +41,27 @@ var l = 0, u = class {
|
|
|
36
41
|
return this.op === "not" ? `not(${this.children[0].toString()})` : `(${this.children.map((e) => e.toString()).join(` ${this.op} `)})`;
|
|
37
42
|
}
|
|
38
43
|
};
|
|
39
|
-
function
|
|
44
|
+
function m(...e) {
|
|
40
45
|
if (e.length === 0) throw Error("and() requires at least one expression");
|
|
41
|
-
return new
|
|
46
|
+
return new p("and", e);
|
|
42
47
|
}
|
|
43
|
-
function
|
|
48
|
+
function h(...e) {
|
|
44
49
|
if (e.length === 0) throw Error("or() requires at least one expression");
|
|
45
|
-
return new
|
|
50
|
+
return new p("or", e);
|
|
46
51
|
}
|
|
47
|
-
function
|
|
48
|
-
return new
|
|
52
|
+
function g(e) {
|
|
53
|
+
return new p("not", [e]);
|
|
49
54
|
}
|
|
50
|
-
function
|
|
51
|
-
return new
|
|
55
|
+
function _(e, t) {
|
|
56
|
+
return new p("implies", [e, t]);
|
|
52
57
|
}
|
|
53
|
-
function
|
|
58
|
+
function v(...e) {
|
|
54
59
|
if (e.length === 0) throw Error("xor() requires at least one expression");
|
|
55
|
-
return new
|
|
60
|
+
return new p("xor", e);
|
|
56
61
|
}
|
|
57
62
|
//#endregion
|
|
58
63
|
//#region src/modeler/constraint.ts
|
|
59
|
-
var
|
|
64
|
+
var y = 0, b = class {
|
|
60
65
|
id;
|
|
61
66
|
lhs;
|
|
62
67
|
sense;
|
|
@@ -65,25 +70,22 @@ var ee = 0, v = class {
|
|
|
65
70
|
slack = null;
|
|
66
71
|
dual = null;
|
|
67
72
|
constructor(e, t, n, r) {
|
|
68
|
-
this.id = ++
|
|
69
|
-
}
|
|
70
|
-
get pi() {
|
|
71
|
-
return this.dual;
|
|
73
|
+
this.id = ++y, this.lhs = e, this.sense = t, this.rhs = n, this.name = r || `c_${this.id}`;
|
|
72
74
|
}
|
|
73
75
|
and(e) {
|
|
74
|
-
return new
|
|
76
|
+
return new p("and", [this, e]);
|
|
75
77
|
}
|
|
76
78
|
or(e) {
|
|
77
|
-
return new
|
|
79
|
+
return new p("or", [this, e]);
|
|
78
80
|
}
|
|
79
81
|
implies(e) {
|
|
80
|
-
return new
|
|
82
|
+
return new p("implies", [this, e]);
|
|
81
83
|
}
|
|
82
84
|
xor(e) {
|
|
83
|
-
return new
|
|
85
|
+
return new p("xor", [this, e]);
|
|
84
86
|
}
|
|
85
87
|
not() {
|
|
86
|
-
return new
|
|
88
|
+
return new p("not", [this]);
|
|
87
89
|
}
|
|
88
90
|
toString() {
|
|
89
91
|
let e = this.sense === "==" ? "=" : this.sense;
|
|
@@ -92,11 +94,11 @@ var ee = 0, v = class {
|
|
|
92
94
|
};
|
|
93
95
|
//#endregion
|
|
94
96
|
//#region src/modeler/quad-expr.ts
|
|
95
|
-
function
|
|
97
|
+
function x(e, t) {
|
|
96
98
|
let n = e.id, r = t.id;
|
|
97
99
|
return n <= r ? `${n}:${r}` : `${r}:${n}`;
|
|
98
100
|
}
|
|
99
|
-
var
|
|
101
|
+
var S = class e {
|
|
100
102
|
linearTerms;
|
|
101
103
|
quadTerms;
|
|
102
104
|
constant;
|
|
@@ -109,7 +111,7 @@ var b = class e {
|
|
|
109
111
|
return new e(this.linearTerms, this.quadTerms, this.constant);
|
|
110
112
|
}
|
|
111
113
|
getQuadCoeff(e, t) {
|
|
112
|
-
let n =
|
|
114
|
+
let n = x(e, t), r = this.quadTerms.get(n);
|
|
113
115
|
return r ? r.coeff : 0;
|
|
114
116
|
}
|
|
115
117
|
add(t) {
|
|
@@ -144,20 +146,45 @@ var b = class e {
|
|
|
144
146
|
return typeof t == "number" ? this.add(-t) : t instanceof e ? this.add(t.neg()) : ("terms" in t && t.terms instanceof Map, this.add(t.mul(-1)));
|
|
145
147
|
}
|
|
146
148
|
mul(t) {
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
let
|
|
150
|
-
|
|
149
|
+
if (typeof t == "number") {
|
|
150
|
+
let n = new e(/* @__PURE__ */ new Map(), /* @__PURE__ */ new Map(), this.constant * t);
|
|
151
|
+
for (let [e, r] of this.linearTerms) {
|
|
152
|
+
let i = r * t;
|
|
153
|
+
Math.abs(i) >= 1e-12 && n.linearTerms.set(e, i);
|
|
154
|
+
}
|
|
155
|
+
for (let [e, r] of this.quadTerms) {
|
|
156
|
+
let i = r.coeff * t;
|
|
157
|
+
Math.abs(i) >= 1e-12 && n.quadTerms.set(e, {
|
|
158
|
+
var1: r.var1,
|
|
159
|
+
var2: r.var2,
|
|
160
|
+
coeff: i
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
return n;
|
|
151
164
|
}
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
});
|
|
165
|
+
if ("id" in t && "name" in t && !("terms" in t) && !("quadTerms" in t)) {
|
|
166
|
+
if (this.quadTerms.size > 0) throw Error("Multiplication creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)");
|
|
167
|
+
let n = new e();
|
|
168
|
+
Math.abs(this.constant) >= 1e-12 && n.linearTerms.set(t, this.constant);
|
|
169
|
+
for (let [r, i] of this.linearTerms) n = n.add(e.fromProduct(r, t, i));
|
|
170
|
+
return n;
|
|
159
171
|
}
|
|
160
|
-
|
|
172
|
+
let n = t, r = "quadTerms" in n ? n.quadTerms.size : 0, i = "quadTerms" in n ? n.linearTerms : n.terms;
|
|
173
|
+
if (this.quadTerms.size > 0 && (r > 0 || i.size > 0) || r > 0 && this.linearTerms.size > 0) throw Error("Multiplication creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)");
|
|
174
|
+
if (r === 0 && i.size === 0) return this.mul(n.constant);
|
|
175
|
+
if (this.quadTerms.size === 0 && this.linearTerms.size === 0) {
|
|
176
|
+
let t = n.mul(this.constant);
|
|
177
|
+
if (t instanceof e) return t;
|
|
178
|
+
let r = new e();
|
|
179
|
+
r.constant = t.constant;
|
|
180
|
+
for (let [e, n] of t.terms) r.linearTerms.set(e, n);
|
|
181
|
+
return r;
|
|
182
|
+
}
|
|
183
|
+
let a = new e();
|
|
184
|
+
if (a.constant = this.constant * n.constant, Math.abs(n.constant) >= 1e-12) for (let [e, t] of this.linearTerms) a.linearTerms.set(e, (a.linearTerms.get(e) || 0) + t * n.constant);
|
|
185
|
+
if (Math.abs(this.constant) >= 1e-12) for (let [e, t] of i) a.linearTerms.set(e, (a.linearTerms.get(e) || 0) + t * this.constant);
|
|
186
|
+
for (let [t, n] of this.linearTerms) for (let [r, o] of i) a = a.add(e.fromProduct(t, r, n * o));
|
|
187
|
+
return a;
|
|
161
188
|
}
|
|
162
189
|
div(e) {
|
|
163
190
|
if (Math.abs(e) < 1e-12) throw Error("Division by zero in QuadExpr.div()");
|
|
@@ -181,15 +208,31 @@ var b = class e {
|
|
|
181
208
|
getValue() {
|
|
182
209
|
return this.value;
|
|
183
210
|
}
|
|
211
|
+
toString() {
|
|
212
|
+
let e = [], t = !0;
|
|
213
|
+
for (let n of this.quadTerms.values()) {
|
|
214
|
+
let r = n.coeff, i = r >= 0 ? t ? "" : "+ " : "- ", a = Math.abs(r), o = a === 1 ? "" : `${a} `;
|
|
215
|
+
n.var1 === n.var2 ? e.push(`${i}${o}${n.var1.name}^2`) : e.push(`${i}${o}${n.var1.name} * ${n.var2.name}`), t = !1;
|
|
216
|
+
}
|
|
217
|
+
for (let [n, r] of this.linearTerms) {
|
|
218
|
+
let i = r >= 0 ? t ? "" : "+ " : "- ", a = Math.abs(r), o = a === 1 ? "" : `${a} `;
|
|
219
|
+
e.push(`${i}${o}${n.name}`), t = !1;
|
|
220
|
+
}
|
|
221
|
+
if (this.constant !== 0 || e.length === 0) {
|
|
222
|
+
let n = this.constant >= 0 ? t ? "" : "+ " : "- ";
|
|
223
|
+
e.push(`${n}${Math.abs(this.constant)}`);
|
|
224
|
+
}
|
|
225
|
+
return e.join(" ") || "0";
|
|
226
|
+
}
|
|
184
227
|
static fromProduct(t, n, r = 1) {
|
|
185
|
-
let i = new e(), a =
|
|
228
|
+
let i = new e(), a = x(t, n);
|
|
186
229
|
return i.quadTerms.set(a, {
|
|
187
230
|
var1: t.id <= n.id ? t : n,
|
|
188
231
|
var2: t.id <= n.id ? n : t,
|
|
189
232
|
coeff: r
|
|
190
233
|
}), i;
|
|
191
234
|
}
|
|
192
|
-
},
|
|
235
|
+
}, C = class e {
|
|
193
236
|
terms;
|
|
194
237
|
constant;
|
|
195
238
|
constructor(e = /* @__PURE__ */ new Map(), t = 0) {
|
|
@@ -199,7 +242,7 @@ var b = class e {
|
|
|
199
242
|
return new e(this.terms, this.constant);
|
|
200
243
|
}
|
|
201
244
|
add(e) {
|
|
202
|
-
if (e instanceof
|
|
245
|
+
if (e instanceof S) return e.add(this);
|
|
203
246
|
let t = this.clone();
|
|
204
247
|
if (typeof e == "number") t.constant += e;
|
|
205
248
|
else if ("terms" in e) {
|
|
@@ -215,7 +258,7 @@ var b = class e {
|
|
|
215
258
|
return t;
|
|
216
259
|
}
|
|
217
260
|
sub(e) {
|
|
218
|
-
return e instanceof
|
|
261
|
+
return e instanceof S ? e.neg().add(this) : typeof e == "number" ? this.add(-e) : ("terms" in e, this.add(e.mul(-1)));
|
|
219
262
|
}
|
|
220
263
|
mul(t) {
|
|
221
264
|
if (typeof t == "number") {
|
|
@@ -226,9 +269,27 @@ var b = class e {
|
|
|
226
269
|
}
|
|
227
270
|
return n;
|
|
228
271
|
}
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
272
|
+
if (t instanceof D || typeof t == "object" && t && "id" in t && !("terms" in t) && !("quadTerms" in t)) {
|
|
273
|
+
let e = t, n = new S();
|
|
274
|
+
Math.abs(this.constant) >= 1e-12 && n.linearTerms.set(e, this.constant);
|
|
275
|
+
for (let [t, r] of this.terms) n = n.add(S.fromProduct(t, e, r));
|
|
276
|
+
return n;
|
|
277
|
+
}
|
|
278
|
+
if (t instanceof S) {
|
|
279
|
+
if (t.quadTerms.size > 0 && this.terms.size > 0) throw Error("Multiplication creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)");
|
|
280
|
+
if (this.terms.size === 0) return t.mul(this.constant);
|
|
281
|
+
let e = new S();
|
|
282
|
+
if (e.constant = this.constant * t.constant, Math.abs(t.constant) >= 1e-12) for (let [n, r] of this.terms) e.linearTerms.set(n, (e.linearTerms.get(n) || 0) + r * t.constant);
|
|
283
|
+
if (Math.abs(this.constant) >= 1e-12) for (let [n, r] of t.linearTerms) e.linearTerms.set(n, (e.linearTerms.get(n) || 0) + r * this.constant);
|
|
284
|
+
for (let [n, r] of this.terms) for (let [i, a] of t.linearTerms) e = e.add(S.fromProduct(n, i, r * a));
|
|
285
|
+
return e;
|
|
286
|
+
}
|
|
287
|
+
if (this.terms.size === 0) return t.mul(this.constant);
|
|
288
|
+
if (t.terms.size === 0) return this.mul(t.constant);
|
|
289
|
+
let n = new S();
|
|
290
|
+
if (n.constant = this.constant * t.constant, Math.abs(t.constant) >= 1e-12) for (let [e, r] of this.terms) n.linearTerms.set(e, (n.linearTerms.get(e) || 0) + r * t.constant);
|
|
291
|
+
if (Math.abs(this.constant) >= 1e-12) for (let [e, r] of t.terms) n.linearTerms.set(e, (n.linearTerms.get(e) || 0) + r * this.constant);
|
|
292
|
+
for (let [e, r] of this.terms) for (let [i, a] of t.terms) n = n.add(S.fromProduct(e, i, r * a));
|
|
232
293
|
return n;
|
|
233
294
|
}
|
|
234
295
|
div(e) {
|
|
@@ -271,7 +332,7 @@ var b = class e {
|
|
|
271
332
|
let i = this.clone(), a = 0;
|
|
272
333
|
typeof n == "number" ? a = n : "terms" in n ? (i = i.sub(new e(n.terms, 0)), a = n.constant) : i = i.sub(n);
|
|
273
334
|
let o = a - i.constant;
|
|
274
|
-
return i.constant = 0, new
|
|
335
|
+
return i.constant = 0, new b(i, t, o, r);
|
|
275
336
|
}
|
|
276
337
|
toString() {
|
|
277
338
|
let e = [], t = !0;
|
|
@@ -286,27 +347,113 @@ var b = class e {
|
|
|
286
347
|
return e.join(" ") || "0";
|
|
287
348
|
}
|
|
288
349
|
};
|
|
289
|
-
function
|
|
290
|
-
let n = /* @__PURE__ */ new Map(), r = 0
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
350
|
+
function w(e, t) {
|
|
351
|
+
let n = /* @__PURE__ */ new Map(), r = 0;
|
|
352
|
+
function i(e) {
|
|
353
|
+
if (e != null) {
|
|
354
|
+
if (typeof e == "number") r += e;
|
|
355
|
+
else if (typeof e == "object" && "terms" in e) {
|
|
356
|
+
let t = e;
|
|
357
|
+
for (let [e, r] of t.terms) {
|
|
358
|
+
let t = n.get(e) || 0;
|
|
359
|
+
n.set(e, t + r);
|
|
360
|
+
}
|
|
361
|
+
r += t.constant;
|
|
362
|
+
} else {
|
|
363
|
+
let t = e, r = n.get(t) || 0;
|
|
364
|
+
n.set(t, r + 1);
|
|
299
365
|
}
|
|
300
|
-
r += t.constant;
|
|
301
|
-
} else if (e) {
|
|
302
|
-
let t = e, r = n.get(t) || 0;
|
|
303
|
-
n.set(t, r + 1);
|
|
304
366
|
}
|
|
305
367
|
}
|
|
368
|
+
if (typeof e == "number") {
|
|
369
|
+
let n = e, r = t;
|
|
370
|
+
for (let e = 0; e < n; e++) i(r(e, e));
|
|
371
|
+
} else {
|
|
372
|
+
let n = 0;
|
|
373
|
+
for (let r of e) i(t ? t(r, n++) : r);
|
|
374
|
+
}
|
|
306
375
|
for (let [e, t] of n) Math.abs(t) < 1e-12 && n.delete(e);
|
|
307
|
-
return new
|
|
376
|
+
return new C(n, r);
|
|
308
377
|
}
|
|
309
|
-
|
|
378
|
+
function ee(e, t) {
|
|
379
|
+
let n = /* @__PURE__ */ new Map(), r = 0;
|
|
380
|
+
function i(e) {
|
|
381
|
+
return typeof e == "object" && !!e && typeof e.id == "number" && typeof e.name == "string" && typeof e.mul == "function" && typeof e.le == "function";
|
|
382
|
+
}
|
|
383
|
+
function a(e) {
|
|
384
|
+
return i(e) || e instanceof C || e instanceof S;
|
|
385
|
+
}
|
|
386
|
+
function o(e, t) {
|
|
387
|
+
if (typeof t == "number") r += e * t;
|
|
388
|
+
else if (t instanceof C) {
|
|
389
|
+
for (let [r, i] of t.terms) {
|
|
390
|
+
let t = n.get(r) || 0;
|
|
391
|
+
n.set(r, t + e * i);
|
|
392
|
+
}
|
|
393
|
+
r += e * t.constant;
|
|
394
|
+
} else if (i(t)) {
|
|
395
|
+
let r = t, i = n.get(r) || 0;
|
|
396
|
+
n.set(r, i + e);
|
|
397
|
+
} else throw Error("Cannot multiply number by non-variable/expression operand in dot().");
|
|
398
|
+
}
|
|
399
|
+
function s(e) {
|
|
400
|
+
return typeof e == "object" && !!e && !Array.isArray(e) && !a(e);
|
|
401
|
+
}
|
|
402
|
+
function c(e, t, n = "") {
|
|
403
|
+
if (e === void 0 || t === void 0 || e === null || t === null) throw Error(`Nullish or undefined operand encountered in dot() at '${n || "root"}'.`);
|
|
404
|
+
if (typeof e == "number") {
|
|
405
|
+
o(e, t);
|
|
406
|
+
return;
|
|
407
|
+
}
|
|
408
|
+
if (typeof t == "number") {
|
|
409
|
+
o(t, e);
|
|
410
|
+
return;
|
|
411
|
+
}
|
|
412
|
+
if (Array.isArray(e) || Array.isArray(t)) {
|
|
413
|
+
if (Array.isArray(e) && Array.isArray(t)) {
|
|
414
|
+
if (e.length !== t.length) throw Error(`Array length mismatch in dot() at '${n || "root"}': received lengths ${e.length} and ${t.length}.`);
|
|
415
|
+
for (let r = 0; r < e.length; r++) c(e[r], t[r], n ? `${n}[${r}]` : `[${r}]`);
|
|
416
|
+
return;
|
|
417
|
+
}
|
|
418
|
+
let r = Array.isArray(e) ? e : t, i = Array.isArray(e) ? t : e;
|
|
419
|
+
if (s(i)) {
|
|
420
|
+
let a = Object.keys(i);
|
|
421
|
+
if (a.length > 0 && a.every((e) => /^\d+$/.test(e))) {
|
|
422
|
+
if (a.length !== r.length) throw Error(`Array length mismatch in dot() at '${n || "root"}': array has length ${r.length}, but object has ${a.length} indices.`);
|
|
423
|
+
let o = [];
|
|
424
|
+
for (let e = 0; e < r.length; e++) !(e in i) && !(String(e) in i) && o.push(e);
|
|
425
|
+
if (o.length > 0) throw Error(`Key mismatch in dot() at '${n || "root"}': missing indices [${o.join(", ")}] in numeric record.`);
|
|
426
|
+
for (let i = 0; i < r.length; i++) c(e[i], t[i], n ? `${n}[${i}]` : `[${i}]`);
|
|
427
|
+
return;
|
|
428
|
+
}
|
|
429
|
+
throw Error(`Type mismatch in dot() at '${n || "root"}': one operand is an Array while the other is an Object with keys [${a.slice(0, 5).join(", ")}].`);
|
|
430
|
+
}
|
|
431
|
+
throw Error(`Type mismatch in dot() at '${n || "root"}': one operand is an Array while the other is not.`);
|
|
432
|
+
}
|
|
433
|
+
if (s(e) && s(t)) {
|
|
434
|
+
let r = Object.keys(e), i = Object.keys(t), a = r.filter((e) => !(e in t)), o = i.filter((t) => !(t in e));
|
|
435
|
+
if (a.length > 0 || o.length > 0) {
|
|
436
|
+
let e = [];
|
|
437
|
+
throw a.length > 0 && e.push(`missing in second operand: [${a.join(", ")}]`), o.length > 0 && e.push(`missing in first operand: [${o.join(", ")}]`), Error(`Key mismatch in dot() at '${n || "root"}': ${e.join("; ")}.`);
|
|
438
|
+
}
|
|
439
|
+
for (let i of r) c(e[i], t[i], n ? `${n}.${i}` : i);
|
|
440
|
+
return;
|
|
441
|
+
}
|
|
442
|
+
throw Error(`Unsupported operand types in dot() at '${n || "root"}'.`);
|
|
443
|
+
}
|
|
444
|
+
c(e, t);
|
|
445
|
+
for (let [e, t] of n) Math.abs(t) < 1e-12 && n.delete(e);
|
|
446
|
+
return new C(n, r);
|
|
447
|
+
}
|
|
448
|
+
//#endregion
|
|
449
|
+
//#region src/modeler/variable.ts
|
|
450
|
+
var T = 0;
|
|
451
|
+
function E(e) {
|
|
452
|
+
if (!e) return "Continuous";
|
|
453
|
+
let t = e.toLowerCase();
|
|
454
|
+
return t === "binary" || t === "bin" ? "Binary" : t === "integer" || t === "int" ? "Integer" : "Continuous";
|
|
455
|
+
}
|
|
456
|
+
var D = class e {
|
|
310
457
|
id;
|
|
311
458
|
name;
|
|
312
459
|
type;
|
|
@@ -315,48 +462,49 @@ var C = S, w = S, T = 0, E = class e {
|
|
|
315
462
|
value = null;
|
|
316
463
|
reducedCost = null;
|
|
317
464
|
constructor(e = {}) {
|
|
318
|
-
this.id = ++T, this.name = e.name || `x_${this.id}`, this.type = e.type
|
|
319
|
-
}
|
|
320
|
-
get x() {
|
|
321
|
-
return this.value;
|
|
322
|
-
}
|
|
323
|
-
get varValue() {
|
|
324
|
-
return this.value;
|
|
465
|
+
this.id = ++T, this.name = e.name || `x_${this.id}`, this.type = E(e.type), this.type === "Binary" ? (this.lb = 0, this.ub = 1) : (this.lb = e.lb === void 0 ? 0 : e.lb, this.ub = e.ub === void 0 ? Infinity : e.ub);
|
|
325
466
|
}
|
|
326
467
|
mul(t) {
|
|
327
|
-
if (typeof t == "number") return new
|
|
328
|
-
if (t instanceof e) return
|
|
329
|
-
|
|
468
|
+
if (typeof t == "number") return new C(/* @__PURE__ */ new Map([[this, t]]), 0);
|
|
469
|
+
if (t instanceof e) return S.fromProduct(this, t, 1);
|
|
470
|
+
if (t instanceof S) {
|
|
471
|
+
if (t.quadTerms.size > 0) throw Error("Multiplication creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)");
|
|
472
|
+
let e = new S();
|
|
473
|
+
Math.abs(t.constant) >= 1e-12 && e.linearTerms.set(this, t.constant);
|
|
474
|
+
for (let [n, r] of t.linearTerms) e = e.add(S.fromProduct(this, n, r));
|
|
475
|
+
return e;
|
|
476
|
+
}
|
|
477
|
+
let n = new S();
|
|
330
478
|
Math.abs(t.constant) >= 1e-12 && n.linearTerms.set(this, t.constant);
|
|
331
479
|
for (let [e, r] of t.terms) {
|
|
332
|
-
let t =
|
|
480
|
+
let t = S.fromProduct(this, e, r);
|
|
333
481
|
n = n.add(t);
|
|
334
482
|
}
|
|
335
483
|
return n;
|
|
336
484
|
}
|
|
337
485
|
add(e) {
|
|
338
|
-
return e instanceof
|
|
486
|
+
return e instanceof S ? e.add(this) : new C(/* @__PURE__ */ new Map([[this, 1]]), 0).add(e);
|
|
339
487
|
}
|
|
340
488
|
sub(e) {
|
|
341
|
-
return e instanceof
|
|
489
|
+
return e instanceof S ? e.neg().add(this) : new C(/* @__PURE__ */ new Map([[this, 1]]), 0).sub(e);
|
|
342
490
|
}
|
|
343
491
|
neg() {
|
|
344
492
|
return this.mul(-1);
|
|
345
493
|
}
|
|
346
494
|
le(e, t) {
|
|
347
|
-
return new
|
|
495
|
+
return new C(/* @__PURE__ */ new Map([[this, 1]]), 0).le(e, t);
|
|
348
496
|
}
|
|
349
497
|
lessThanOrEqual(e, t) {
|
|
350
498
|
return this.le(e, t);
|
|
351
499
|
}
|
|
352
500
|
ge(e, t) {
|
|
353
|
-
return new
|
|
501
|
+
return new C(/* @__PURE__ */ new Map([[this, 1]]), 0).ge(e, t);
|
|
354
502
|
}
|
|
355
503
|
greaterThanOrEqual(e, t) {
|
|
356
504
|
return this.ge(e, t);
|
|
357
505
|
}
|
|
358
506
|
eq(e, t) {
|
|
359
|
-
return new
|
|
507
|
+
return new C(/* @__PURE__ */ new Map([[this, 1]]), 0).eq(e, t);
|
|
360
508
|
}
|
|
361
509
|
equalTo(e, t) {
|
|
362
510
|
return this.eq(e, t);
|
|
@@ -367,7 +515,7 @@ var C = S, w = S, T = 0, E = class e {
|
|
|
367
515
|
};
|
|
368
516
|
//#endregion
|
|
369
517
|
//#region src/modeler/parser.ts
|
|
370
|
-
function
|
|
518
|
+
function O(e) {
|
|
371
519
|
let t = [], n = 0, r = e.length;
|
|
372
520
|
for (; n < r;) {
|
|
373
521
|
let i = e[n];
|
|
@@ -383,9 +531,16 @@ function te(e) {
|
|
|
383
531
|
type: "MINUS",
|
|
384
532
|
value: "-"
|
|
385
533
|
}), n++;
|
|
386
|
-
else if (i === "*") t.push({
|
|
534
|
+
else if (i === "*") n + 1 < r && e[n + 1] === "*" ? (t.push({
|
|
535
|
+
type: "CARET",
|
|
536
|
+
value: "**"
|
|
537
|
+
}), n += 2) : (t.push({
|
|
387
538
|
type: "STAR",
|
|
388
539
|
value: "*"
|
|
540
|
+
}), n++);
|
|
541
|
+
else if (i === "^") t.push({
|
|
542
|
+
type: "CARET",
|
|
543
|
+
value: "^"
|
|
389
544
|
}), n++;
|
|
390
545
|
else if (i === "/") t.push({
|
|
391
546
|
type: "SLASH",
|
|
@@ -423,7 +578,24 @@ function te(e) {
|
|
|
423
578
|
}
|
|
424
579
|
return t;
|
|
425
580
|
}
|
|
426
|
-
|
|
581
|
+
function k(e, t) {
|
|
582
|
+
return e instanceof S ? e.add(t) : t instanceof S ? t.add(e) : e.add(t);
|
|
583
|
+
}
|
|
584
|
+
function te(e, t) {
|
|
585
|
+
return e instanceof S ? e.sub(t) : t instanceof S ? t.neg().add(e) : e.sub(t);
|
|
586
|
+
}
|
|
587
|
+
function A(e, t) {
|
|
588
|
+
let n = e instanceof S ? e.quadTerms : /* @__PURE__ */ new Map(), r = t instanceof S ? t.quadTerms : /* @__PURE__ */ new Map(), i = e instanceof S ? e.linearTerms : e.terms, a = t instanceof S ? t.linearTerms : t.terms;
|
|
589
|
+
if (n.size > 0 && (r.size > 0 || a.size > 0) || r.size > 0 && (n.size > 0 || i.size > 0)) throw Error("Multiplication creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)");
|
|
590
|
+
if (n.size === 0 && i.size === 0) return t.mul(e.constant);
|
|
591
|
+
if (r.size === 0 && a.size === 0) return e.mul(t.constant);
|
|
592
|
+
let o = new S();
|
|
593
|
+
if (o.constant = e.constant * t.constant, Math.abs(t.constant) >= 1e-12) for (let [e, n] of i) o.linearTerms.set(e, (o.linearTerms.get(e) || 0) + n * t.constant);
|
|
594
|
+
if (Math.abs(e.constant) >= 1e-12) for (let [t, n] of a) o.linearTerms.set(t, (o.linearTerms.get(t) || 0) + n * e.constant);
|
|
595
|
+
for (let [e, t] of i) for (let [n, r] of a) o = o.add(S.fromProduct(e, n, t * r));
|
|
596
|
+
return o;
|
|
597
|
+
}
|
|
598
|
+
var j = class {
|
|
427
599
|
tokens;
|
|
428
600
|
pos = 0;
|
|
429
601
|
resolver;
|
|
@@ -444,11 +616,11 @@ var ne = class {
|
|
|
444
616
|
for (; this.pos < this.tokens.length;) {
|
|
445
617
|
let t = this.peek();
|
|
446
618
|
if (!t) break;
|
|
447
|
-
if (t.type === "PLUS") this.consume(), e = e
|
|
448
|
-
else if (t.type === "MINUS") this.consume(), e = e
|
|
619
|
+
if (t.type === "PLUS") this.consume(), e = k(e, this.parseTerm());
|
|
620
|
+
else if (t.type === "MINUS") this.consume(), e = te(e, this.parseTerm());
|
|
449
621
|
else break;
|
|
450
622
|
}
|
|
451
|
-
return e;
|
|
623
|
+
return e instanceof S && e.quadTerms.size === 0 ? new C(e.linearTerms, e.constant) : e;
|
|
452
624
|
}
|
|
453
625
|
parseTerm() {
|
|
454
626
|
let e = this.parseFactor();
|
|
@@ -458,57 +630,83 @@ var ne = class {
|
|
|
458
630
|
if (t.type === "STAR") {
|
|
459
631
|
this.consume();
|
|
460
632
|
let t = this.parseFactor();
|
|
461
|
-
e =
|
|
633
|
+
e = A(e, t);
|
|
462
634
|
} else if (t.type === "SLASH") {
|
|
463
635
|
this.consume();
|
|
464
|
-
let t = this.parseFactor();
|
|
465
|
-
if (
|
|
636
|
+
let t = this.parseFactor(), n = t instanceof S ? t.linearTerms : t.terms, r = t instanceof S ? t.quadTerms.size : 0;
|
|
637
|
+
if (n.size > 0 || r > 0) throw Error("Cannot divide by variable in expression");
|
|
466
638
|
if (Math.abs(t.constant) < 1e-12) throw Error("Division by zero in expression");
|
|
467
639
|
e = e.div(t.constant);
|
|
468
640
|
} else break;
|
|
469
641
|
}
|
|
470
642
|
return e;
|
|
471
643
|
}
|
|
472
|
-
multiplyExpressions(e, t) {
|
|
473
|
-
if (e.terms.size > 0 && t.terms.size > 0) throw Error("Multiplication of two variables creates a non-linear term (not allowed in MILP/LP)");
|
|
474
|
-
return e.terms.size === 0 ? t.mul(e.constant) : e.mul(t.constant);
|
|
475
|
-
}
|
|
476
644
|
parseFactor() {
|
|
477
645
|
let e = this.peek();
|
|
478
646
|
if (!e) throw Error("Unexpected end of expression");
|
|
479
647
|
if (e.type === "PLUS") return this.consume(), this.parseFactor();
|
|
480
648
|
if (e.type === "MINUS") return this.consume(), this.parseFactor().neg();
|
|
649
|
+
let t;
|
|
481
650
|
if (e.type === "NUMBER") {
|
|
482
651
|
this.consume();
|
|
483
|
-
let
|
|
484
|
-
if (this.peek()?.type === "IDENT") {
|
|
485
|
-
let e
|
|
486
|
-
|
|
652
|
+
let n = parseFloat(e.value);
|
|
653
|
+
if (this.peek()?.type === "IDENT" || this.peek()?.type === "LPAREN") {
|
|
654
|
+
let e;
|
|
655
|
+
if (this.peek()?.type === "IDENT") {
|
|
656
|
+
let t = this.consume(), n = this.resolve(t.value);
|
|
657
|
+
e = n instanceof D || "id" in n && !("terms" in n) && !("quadTerms" in n) ? new C(/* @__PURE__ */ new Map([[n, 1]]), 0) : n.clone();
|
|
658
|
+
} else this.consume("LPAREN"), e = this.parseExpression(), this.consume("RPAREN");
|
|
659
|
+
return this.applyPower(e).mul(n);
|
|
487
660
|
}
|
|
488
|
-
|
|
489
|
-
}
|
|
490
|
-
|
|
661
|
+
t = new C(/* @__PURE__ */ new Map(), n);
|
|
662
|
+
} else if (e.type === "IDENT") {
|
|
663
|
+
this.consume();
|
|
664
|
+
let n = this.resolve(e.value);
|
|
665
|
+
t = n instanceof D || "id" in n && !("terms" in n) && !("quadTerms" in n) ? new C(/* @__PURE__ */ new Map([[n, 1]]), 0) : n.clone();
|
|
666
|
+
} else if (e.type === "LPAREN") this.consume("LPAREN"), t = this.parseExpression(), this.consume("RPAREN");
|
|
667
|
+
else throw Error(`Unexpected token '${e.value}' in expression`);
|
|
668
|
+
return this.applyPower(t);
|
|
669
|
+
}
|
|
670
|
+
applyPower(e) {
|
|
671
|
+
if (this.peek()?.type !== "CARET") return e;
|
|
672
|
+
let t = [];
|
|
673
|
+
for (; this.peek()?.type === "CARET";) {
|
|
674
|
+
this.consume();
|
|
675
|
+
let e = this.peek();
|
|
676
|
+
if (!e || e.type !== "NUMBER") throw Error("Exponent must be a non-negative integer number");
|
|
491
677
|
this.consume();
|
|
492
|
-
let
|
|
493
|
-
|
|
678
|
+
let n = parseFloat(e.value);
|
|
679
|
+
if (!Number.isInteger(n) || n < 0) throw Error("Exponent must be a non-negative integer");
|
|
680
|
+
t.push(n);
|
|
494
681
|
}
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
682
|
+
let n = t[t.length - 1];
|
|
683
|
+
for (let e = t.length - 2; e >= 0; e--) n = t[e] ** +n;
|
|
684
|
+
if (!Number.isFinite(n) || n < 0) throw Error("Exponent creates an invalid or out-of-range power");
|
|
685
|
+
let r = e instanceof S, i = r ? e.quadTerms.size : 0, a = r ? e.linearTerms.size : e.terms.size;
|
|
686
|
+
if (i === 0 && a === 0) {
|
|
687
|
+
let t = e.constant ** +n;
|
|
688
|
+
return new C(/* @__PURE__ */ new Map(), t);
|
|
499
689
|
}
|
|
500
|
-
|
|
690
|
+
if (n === 0) return new C(/* @__PURE__ */ new Map(), 1);
|
|
691
|
+
if (n === 1) return e;
|
|
692
|
+
if (n === 2) return A(e, e);
|
|
693
|
+
throw Error(`Exponent ${n} creates a non-linear term of degree > 2 (not allowed in MILP/LP/QP)`);
|
|
501
694
|
}
|
|
502
|
-
|
|
695
|
+
getRemainingToken() {
|
|
696
|
+
return this.peek();
|
|
697
|
+
}
|
|
698
|
+
resolve(e) {
|
|
503
699
|
let t = this.resolver(e);
|
|
504
700
|
if (!t) throw Error(`Unknown variable '${e}' in expression`);
|
|
505
701
|
return t;
|
|
506
702
|
}
|
|
507
703
|
};
|
|
508
|
-
function
|
|
509
|
-
|
|
704
|
+
function M(e, t) {
|
|
705
|
+
let n = new j(O(e), t), r = n.parseExpression(), i = n.getRemainingToken();
|
|
706
|
+
if (i) throw Error(`Unexpected token '${i.value}' after expression in "${e}"`);
|
|
707
|
+
return r;
|
|
510
708
|
}
|
|
511
|
-
function
|
|
709
|
+
function N(e, t, n) {
|
|
512
710
|
let r = e.match(/(<=|>=|==|=<|=>|=)/);
|
|
513
711
|
if (!r) throw Error(`Constraint must contain a comparison operator (<=, >=, ==, =): "${e}"`);
|
|
514
712
|
let i = r[0], a = r.index, o = e.substring(0, a).trim(), s = e.substring(a + i.length).trim(), c;
|
|
@@ -516,20 +714,19 @@ function O(e, t, n) {
|
|
|
516
714
|
else if (i === ">=" || i === "=>") c = ">=";
|
|
517
715
|
else if (i === "==" || i === "=") c = "==";
|
|
518
716
|
else throw Error(`Unsupported operator "${i}"`);
|
|
519
|
-
let l =
|
|
520
|
-
|
|
717
|
+
let l = M(o, t), u = M(s, t);
|
|
718
|
+
if (l instanceof S && l.quadTerms.size > 0 || u instanceof S && u.quadTerms.size > 0) throw Error("Quadratic constraints are not supported (only linear constraints are allowed in MILP/LP/QP)");
|
|
719
|
+
let d = l instanceof S ? new C(l.linearTerms, l.constant) : l, f = u instanceof S ? new C(u.linearTerms, u.constant) : u;
|
|
720
|
+
return c === "<=" ? d.le(f, n) : c === ">=" ? d.ge(f, n) : d.eq(f, n);
|
|
521
721
|
}
|
|
522
|
-
function
|
|
722
|
+
function P(e, t) {
|
|
523
723
|
let n = /* @__PURE__ */ new Map(), r = "";
|
|
524
724
|
for (let i = 0; i < e.length; i++) if (r += e[i], i < t.length) {
|
|
525
725
|
let e = t[i];
|
|
526
726
|
if (typeof e == "number") r += `(${e})`;
|
|
527
|
-
else if (e instanceof
|
|
528
|
-
let t = `
|
|
727
|
+
else if (e instanceof D || e instanceof C || e instanceof S || typeof e == "object" && e && ("id" in e || "terms" in e || "quadTerms" in e)) {
|
|
728
|
+
let t = `__ph_${i}__`;
|
|
529
729
|
n.set(t, e), r += t;
|
|
530
|
-
} else if (e instanceof x) {
|
|
531
|
-
`${i}`, r += `(${e.toString()})`;
|
|
532
|
-
for (let [t] of e.terms) n.set(t.name, t);
|
|
533
730
|
}
|
|
534
731
|
}
|
|
535
732
|
return {
|
|
@@ -537,42 +734,42 @@ function k(e, t) {
|
|
|
537
734
|
resolver: (e) => n.get(e)
|
|
538
735
|
};
|
|
539
736
|
}
|
|
540
|
-
function
|
|
541
|
-
let { fullText: n, resolver: r } =
|
|
542
|
-
return
|
|
737
|
+
function F(e, ...t) {
|
|
738
|
+
let { fullText: n, resolver: r } = P(e, t);
|
|
739
|
+
return N(n, r);
|
|
543
740
|
}
|
|
544
|
-
function
|
|
545
|
-
let { fullText: n, resolver: r } =
|
|
546
|
-
return /(<=|>=|==|=<|=>|=)/.test(n) ?
|
|
741
|
+
function I(e, ...t) {
|
|
742
|
+
let { fullText: n, resolver: r } = P(e, t);
|
|
743
|
+
return /(<=|>=|==|=<|=>|=)/.test(n) ? N(n, r) : M(n, r);
|
|
547
744
|
}
|
|
548
745
|
//#endregion
|
|
549
746
|
//#region src/modeler/lp-writer.ts
|
|
550
|
-
function
|
|
747
|
+
function L(e, t, n) {
|
|
551
748
|
let r = e.replace(/[^a-zA-Z0-9_]/g, "_");
|
|
552
749
|
return /^[0-9]/.test(r) && (r = `${t}_${r}`), (!r || r.length === 0) && (r = `${t}_${n}`), r;
|
|
553
750
|
}
|
|
554
|
-
function
|
|
751
|
+
function R(e) {
|
|
555
752
|
let { sense: t, objective: n, constraints: r, variables: i } = e, a = /* @__PURE__ */ new Map(), o = /* @__PURE__ */ new Map(), s = /* @__PURE__ */ new Map(), c = /* @__PURE__ */ new Set();
|
|
556
753
|
for (let e of i) {
|
|
557
|
-
let t =
|
|
754
|
+
let t = L(e.name, "x", e.id), n = t, r = 1;
|
|
558
755
|
for (; c.has(n);) n = `${t}_${r++}`;
|
|
559
756
|
c.add(n), o.set(e, n), a.set(n, e);
|
|
560
757
|
}
|
|
561
758
|
let l = /* @__PURE__ */ new Set(), u = /* @__PURE__ */ new Map();
|
|
562
759
|
for (let e of r) {
|
|
563
|
-
let t =
|
|
760
|
+
let t = L(e.name, "c", e.id), n = t, r = 1;
|
|
564
761
|
for (; l.has(n);) n = `${t}_${r++}`;
|
|
565
762
|
l.add(n), u.set(e, n), s.set(n, e);
|
|
566
763
|
}
|
|
567
764
|
let d = [];
|
|
568
|
-
d.push(t === "
|
|
569
|
-
let f = [], p = !0, m = n instanceof
|
|
765
|
+
d.push(t && t.toLowerCase() === "maximize" ? "Maximize" : "Minimize");
|
|
766
|
+
let f = [], p = !0, m = n instanceof S ? n.linearTerms : n.terms;
|
|
570
767
|
if (m) for (let [e, t] of m) {
|
|
571
768
|
if (Math.abs(t) < 1e-12) continue;
|
|
572
769
|
let n = o.get(e), r = t >= 0 ? p ? "" : "+ " : "- ", i = Math.abs(t), a = i === 1 ? "" : `${i} `;
|
|
573
770
|
f.push(`${r}${a}${n}`), p = !1;
|
|
574
771
|
}
|
|
575
|
-
if (n instanceof
|
|
772
|
+
if (n instanceof S && n.quadTerms.size > 0) {
|
|
576
773
|
let e = [], t = !0;
|
|
577
774
|
for (let r of n.quadTerms.values()) {
|
|
578
775
|
if (Math.abs(r.coeff) < 1e-12) continue;
|
|
@@ -624,38 +821,38 @@ function j(e) {
|
|
|
624
821
|
}
|
|
625
822
|
//#endregion
|
|
626
823
|
//#region src/modeler/solvers/registry.ts
|
|
627
|
-
var
|
|
628
|
-
|
|
629
|
-
var
|
|
630
|
-
function
|
|
631
|
-
|
|
824
|
+
var z = Symbol.for("washi.solverRegistry"), B = Symbol.for("washi.defaultSolverFactory"), V = globalThis;
|
|
825
|
+
V[z] || (V[z] = /* @__PURE__ */ new Map());
|
|
826
|
+
var H = V[z];
|
|
827
|
+
function U(e, t) {
|
|
828
|
+
H.set(e.toLowerCase(), t);
|
|
632
829
|
}
|
|
633
|
-
function
|
|
830
|
+
function W(e) {
|
|
634
831
|
if (typeof e == "string") {
|
|
635
|
-
let t =
|
|
832
|
+
let t = H.get(e.toLowerCase());
|
|
636
833
|
if (!t) throw Error(`Solver '${e}' is not registered.`);
|
|
637
|
-
|
|
638
|
-
} else
|
|
834
|
+
V[B] = t;
|
|
835
|
+
} else V[B] = typeof e == "function" ? e : () => e;
|
|
639
836
|
}
|
|
640
|
-
function
|
|
837
|
+
function G(e, t) {
|
|
641
838
|
if (!e) {
|
|
642
|
-
let e =
|
|
643
|
-
if (!e) throw Error(`No default solver available. Available solvers: ${
|
|
839
|
+
let e = V[B] || H.get("highs");
|
|
840
|
+
if (!e) throw Error(`No default solver available. Available solvers: ${K().join(", ")}`);
|
|
644
841
|
return e(t);
|
|
645
842
|
}
|
|
646
843
|
if (typeof e == "string") {
|
|
647
|
-
let n = e.toLowerCase(), r =
|
|
648
|
-
if (!r) throw Error(n === "glpk" ? `Solver 'glpk' not found. Available solvers: ${
|
|
844
|
+
let n = e.toLowerCase(), r = H.get(n);
|
|
845
|
+
if (!r) throw Error(n === "glpk" ? `Solver 'glpk' not found. Available solvers: ${K().join(", ")}. Please import '@ohtaman/washi/solvers/glpk' before selecting this solver.` : n === "z3" ? `Solver 'z3' not found. Available solvers: ${K().join(", ")}. Please import '@ohtaman/washi/solvers/z3' before selecting this solver.` : `Solver '${e}' not found. Available solvers: ${K().join(", ")}`);
|
|
649
846
|
return r(t);
|
|
650
847
|
}
|
|
651
848
|
return e;
|
|
652
849
|
}
|
|
653
|
-
function
|
|
654
|
-
return Array.from(
|
|
850
|
+
function K() {
|
|
851
|
+
return Array.from(H.keys());
|
|
655
852
|
}
|
|
656
853
|
//#endregion
|
|
657
854
|
//#region \0washi-browser-worker-factory
|
|
658
|
-
function
|
|
855
|
+
function q() {
|
|
659
856
|
let e = r("highs-worker.js");
|
|
660
857
|
if (new URL(e).origin === window.location.origin) return new Worker(e, { type: "module" });
|
|
661
858
|
let t = URL.createObjectURL(new Blob(["import " + JSON.stringify(e) + ";"], { type: "text/javascript" }));
|
|
@@ -668,41 +865,41 @@ function ae() {
|
|
|
668
865
|
}
|
|
669
866
|
//#endregion
|
|
670
867
|
//#region src/modeler/solvers/highs/worker-client.ts
|
|
671
|
-
var
|
|
672
|
-
function
|
|
868
|
+
var J = null, Y = 0, X = /* @__PURE__ */ new Map();
|
|
869
|
+
function Z() {
|
|
673
870
|
if (typeof window > "u" || typeof Worker > "u") return null;
|
|
674
|
-
if (!
|
|
675
|
-
|
|
676
|
-
let e =
|
|
677
|
-
|
|
678
|
-
let { type: t, id: n, result: r, runTime: i, error: a } = e.data, o =
|
|
679
|
-
o && (
|
|
871
|
+
if (!J) try {
|
|
872
|
+
J = q();
|
|
873
|
+
let e = J;
|
|
874
|
+
J.onmessage = (e) => {
|
|
875
|
+
let { type: t, id: n, result: r, runTime: i, error: a } = e.data, o = X.get(n);
|
|
876
|
+
o && (X.delete(n), t === "SOLVE_SUCCESS" ? o.resolve({
|
|
680
877
|
result: r,
|
|
681
878
|
runTime: i
|
|
682
879
|
}) : o.reject(Error(a || "Worker solve failed")));
|
|
683
880
|
};
|
|
684
881
|
let t = (t) => {
|
|
685
|
-
if (
|
|
686
|
-
|
|
687
|
-
for (let e of
|
|
688
|
-
|
|
882
|
+
if (J === e) {
|
|
883
|
+
J = null, e.terminate();
|
|
884
|
+
for (let e of X.values()) e.reject(t);
|
|
885
|
+
X.clear();
|
|
689
886
|
}
|
|
690
887
|
};
|
|
691
|
-
|
|
888
|
+
J.onerror = (e) => t(/* @__PURE__ */ Error(`[WaSHI] HiGHS Worker failed to load or execute. Check Worker assets, CORS and CSP. ${e?.message || ""}`)), J.onmessageerror = () => t(/* @__PURE__ */ Error("[WaSHI] Could not deserialize the HiGHS Worker response."));
|
|
692
889
|
} catch {
|
|
693
|
-
|
|
890
|
+
J = null;
|
|
694
891
|
}
|
|
695
|
-
return
|
|
892
|
+
return J;
|
|
696
893
|
}
|
|
697
|
-
async function
|
|
698
|
-
let r = await a(n.wasmUrl), i = n.useWorker ?? typeof window < "u" ?
|
|
894
|
+
async function ne(e, n = {}) {
|
|
895
|
+
let r = await a(n.wasmUrl), i = n.useWorker ?? typeof window < "u" ? Z() : null;
|
|
699
896
|
if (!i) return t(e, n);
|
|
700
897
|
let o = {
|
|
701
898
|
...n,
|
|
702
899
|
wasmUrl: r
|
|
703
|
-
}, s = `req_${++
|
|
900
|
+
}, s = `req_${++Y}`;
|
|
704
901
|
return new Promise((t, n) => {
|
|
705
|
-
|
|
902
|
+
X.set(s, {
|
|
706
903
|
resolve: t,
|
|
707
904
|
reject: n
|
|
708
905
|
});
|
|
@@ -714,13 +911,13 @@ async function W(e, n = {}) {
|
|
|
714
911
|
options: o
|
|
715
912
|
});
|
|
716
913
|
} catch (e) {
|
|
717
|
-
|
|
914
|
+
X.delete(s), n(e);
|
|
718
915
|
}
|
|
719
916
|
});
|
|
720
917
|
}
|
|
721
918
|
//#endregion
|
|
722
919
|
//#region src/modeler/solvers/highs/solver.ts
|
|
723
|
-
function
|
|
920
|
+
function re(e) {
|
|
724
921
|
if (typeof e != "string") return "Unknown";
|
|
725
922
|
let t = e.trim();
|
|
726
923
|
if (!t) return "Unknown";
|
|
@@ -749,7 +946,7 @@ function G(e) {
|
|
|
749
946
|
let n = t.toLowerCase();
|
|
750
947
|
return n.includes("infeasible") && n.includes("unbounded") ? "Unknown" : n.includes("infeasible") ? "Infeasible" : n.includes("unbounded") ? "Unbounded" : n.includes("time limit") || n.includes("timelimit") ? "TimeLimit" : n.includes("iteration limit") || n.includes("iterationlimit") ? "IterationLimit" : n.includes("error") ? "Error" : n === "optimal" ? "Optimal" : "Unknown";
|
|
751
948
|
}
|
|
752
|
-
var
|
|
949
|
+
var Q = class e {
|
|
753
950
|
static capabilities = {
|
|
754
951
|
supportsMIP: !0,
|
|
755
952
|
supportsQP: !0
|
|
@@ -765,7 +962,18 @@ var K = class e {
|
|
|
765
962
|
let r = {
|
|
766
963
|
...this.options,
|
|
767
964
|
...n
|
|
768
|
-
}, { lpString: i, nameToVar: a, nameToConstraint: o } = t, { result: s, runTime: c } = await
|
|
965
|
+
}, { lpString: i, nameToVar: a, nameToConstraint: o } = t, { result: s, runTime: c } = await ne(i, r), l = re(s?.Status);
|
|
966
|
+
if (l === "Infeasible" || l === "Unbounded") return {
|
|
967
|
+
status: l,
|
|
968
|
+
objectiveValue: null,
|
|
969
|
+
values: {},
|
|
970
|
+
reducedCosts: {},
|
|
971
|
+
duals: {},
|
|
972
|
+
slacks: {},
|
|
973
|
+
runTime: c,
|
|
974
|
+
raw: s
|
|
975
|
+
};
|
|
976
|
+
let u = s.ObjectiveValue, d = typeof u == "number" ? u + e.objective.constant : null, f = {}, p = {}, m = {}, h = {};
|
|
769
977
|
if (s.Columns) for (let [e, t] of Object.entries(s.Columns)) {
|
|
770
978
|
let n = a.get(e);
|
|
771
979
|
if (n) {
|
|
@@ -794,14 +1002,14 @@ var K = class e {
|
|
|
794
1002
|
raw: s
|
|
795
1003
|
};
|
|
796
1004
|
}
|
|
797
|
-
},
|
|
798
|
-
function
|
|
799
|
-
|
|
1005
|
+
}, ie = Q;
|
|
1006
|
+
function ae() {
|
|
1007
|
+
U("highs", (e) => new Q(e)), W((e) => new Q(e));
|
|
800
1008
|
}
|
|
801
|
-
|
|
1009
|
+
ae();
|
|
802
1010
|
//#endregion
|
|
803
1011
|
//#region src/modeler/solvers/mock.ts
|
|
804
|
-
var
|
|
1012
|
+
var $ = class {
|
|
805
1013
|
name;
|
|
806
1014
|
capabilities;
|
|
807
1015
|
options;
|
|
@@ -828,13 +1036,13 @@ var J = class {
|
|
|
828
1036
|
};
|
|
829
1037
|
}
|
|
830
1038
|
};
|
|
831
|
-
function
|
|
832
|
-
|
|
1039
|
+
function oe() {
|
|
1040
|
+
U("mock", (e) => new $(e));
|
|
833
1041
|
}
|
|
834
|
-
|
|
1042
|
+
oe();
|
|
835
1043
|
//#endregion
|
|
836
1044
|
//#region src/modeler/model.ts
|
|
837
|
-
var
|
|
1045
|
+
var se = class {
|
|
838
1046
|
name;
|
|
839
1047
|
sense;
|
|
840
1048
|
objective;
|
|
@@ -845,6 +1053,8 @@ var Y = class {
|
|
|
845
1053
|
unsatCore = [];
|
|
846
1054
|
values = /* @__PURE__ */ new Map();
|
|
847
1055
|
varMapByName = /* @__PURE__ */ new Map();
|
|
1056
|
+
boolVarMapByName = /* @__PURE__ */ new Map();
|
|
1057
|
+
boolVarPrefixCounters = /* @__PURE__ */ new Map();
|
|
848
1058
|
constrMapByName = /* @__PURE__ */ new Map();
|
|
849
1059
|
status = "NotSolved";
|
|
850
1060
|
objectiveValue = null;
|
|
@@ -856,7 +1066,7 @@ var Y = class {
|
|
|
856
1066
|
n = typeof e == "string" ? {
|
|
857
1067
|
...t,
|
|
858
1068
|
name: e
|
|
859
|
-
} : e, this.name = n.name || "OptimizationModel", this.sense = n.sense
|
|
1069
|
+
} : e, this.name = n.name || "OptimizationModel", this.sense = l(n.sense), this.objective = new C(), n.solver && (this.solver = G(n.solver));
|
|
860
1070
|
}
|
|
861
1071
|
get vars() {
|
|
862
1072
|
return this.variables;
|
|
@@ -870,70 +1080,120 @@ var Y = class {
|
|
|
870
1080
|
get numConstrs() {
|
|
871
1081
|
return this.constraints.length;
|
|
872
1082
|
}
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
1083
|
+
createDomainVars(e, t, n, r) {
|
|
1084
|
+
if (typeof n == "number" || Array.isArray(n)) {
|
|
1085
|
+
let i = typeof t == "number" ? Array.from({ length: t }, (e, t) => t) : t, a = typeof n == "number" ? Array.from({ length: n }, (e, t) => t) : n, o = r || {}, s = o.prefix || o.name || "x", c = {};
|
|
1086
|
+
for (let t of i) {
|
|
1087
|
+
c[t] = {};
|
|
1088
|
+
for (let n of a) c[t][n] = this.addVar({
|
|
1089
|
+
...o,
|
|
1090
|
+
type: e,
|
|
1091
|
+
name: `${s}_${t}_${n}`
|
|
1092
|
+
});
|
|
1093
|
+
}
|
|
1094
|
+
return c;
|
|
1095
|
+
}
|
|
1096
|
+
if (typeof t == "string") {
|
|
1097
|
+
let r = n || {};
|
|
1098
|
+
return this.addVar({
|
|
1099
|
+
...r,
|
|
1100
|
+
type: e,
|
|
1101
|
+
name: t
|
|
1102
|
+
});
|
|
1103
|
+
}
|
|
1104
|
+
let i = n || {}, a = i.prefix || i.name;
|
|
1105
|
+
if (typeof t == "number") {
|
|
1106
|
+
let n = [], r = a || "x";
|
|
1107
|
+
for (let a = 0; a < t; a++) n.push(this.addVar({
|
|
1108
|
+
...i,
|
|
1109
|
+
type: e,
|
|
1110
|
+
name: `${r}_${a}`
|
|
1111
|
+
}));
|
|
1112
|
+
return n;
|
|
1113
|
+
}
|
|
1114
|
+
if (Array.isArray(t) || t && typeof t[Symbol.iterator] == "function") {
|
|
1115
|
+
let n = {};
|
|
1116
|
+
for (let r of t) {
|
|
1117
|
+
let t = a ? `${a}_${r}` : `${r}`;
|
|
1118
|
+
n[r] = this.addVar({
|
|
1119
|
+
...i,
|
|
1120
|
+
type: e,
|
|
1121
|
+
name: t
|
|
1122
|
+
});
|
|
1123
|
+
}
|
|
1124
|
+
return n;
|
|
1125
|
+
}
|
|
1126
|
+
throw Error(`Invalid arguments provided for ${e.toLowerCase()} variable creation`);
|
|
1127
|
+
}
|
|
1128
|
+
binary(e, t, n) {
|
|
1129
|
+
return this.createDomainVars("Binary", e, t, n);
|
|
1130
|
+
}
|
|
1131
|
+
integer(e, t, n) {
|
|
1132
|
+
return this.createDomainVars("Integer", e, t, n);
|
|
1133
|
+
}
|
|
1134
|
+
continuous(e, t, n) {
|
|
1135
|
+
return this.createDomainVars("Continuous", e, t, n);
|
|
1136
|
+
}
|
|
1137
|
+
bool(e, t, n) {
|
|
886
1138
|
if (typeof t == "number" || Array.isArray(t)) {
|
|
887
|
-
let r = typeof e == "number" ? Array.from({ length: e }, (e, t) => t) : e, i = typeof t == "number" ? Array.from({ length: t }, (e, t) => t) : t, a = n || {}, o = a.prefix || a.name || "
|
|
1139
|
+
let r = typeof e == "number" ? Array.from({ length: e }, (e, t) => t) : e, i = typeof t == "number" ? Array.from({ length: t }, (e, t) => t) : t, a = n || {}, o = a.prefix || a.name || "p", s = {};
|
|
888
1140
|
for (let e of r) {
|
|
889
1141
|
s[e] = {};
|
|
890
|
-
for (let t of i) s[e][t] = this.
|
|
891
|
-
...a,
|
|
892
|
-
name: `${o}_${e}_${t}`
|
|
893
|
-
});
|
|
1142
|
+
for (let t of i) s[e][t] = this.createBoolVar(`${o}_${e}_${t}`);
|
|
894
1143
|
}
|
|
895
1144
|
return s;
|
|
896
1145
|
}
|
|
1146
|
+
if (typeof e == "string" || e === void 0) return this.createBoolVar(e);
|
|
897
1147
|
let r = t || {}, i = r.prefix || r.name;
|
|
898
1148
|
if (typeof e == "number") {
|
|
899
|
-
let t = [], n = i || "
|
|
900
|
-
for (let
|
|
901
|
-
...r,
|
|
902
|
-
name: `${n}_${i}`
|
|
903
|
-
}));
|
|
1149
|
+
let t = [], n = i || "p";
|
|
1150
|
+
for (let r = 0; r < e; r++) t.push(this.createBoolVar(this.getNextBoolVarName(n)));
|
|
904
1151
|
return t;
|
|
905
1152
|
}
|
|
906
|
-
{
|
|
1153
|
+
if (Array.isArray(e) || e && typeof e[Symbol.iterator] == "function") {
|
|
907
1154
|
let t = {};
|
|
908
1155
|
for (let n of e) {
|
|
909
1156
|
let e = i ? `${i}_${n}` : `${n}`;
|
|
910
|
-
t[n] = this.
|
|
911
|
-
...r,
|
|
912
|
-
name: e
|
|
913
|
-
});
|
|
1157
|
+
t[n] = this.createBoolVar(e);
|
|
914
1158
|
}
|
|
915
1159
|
return t;
|
|
916
1160
|
}
|
|
1161
|
+
throw Error("Invalid arguments provided for boolean variable creation");
|
|
917
1162
|
}
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
1163
|
+
hasVarName(e) {
|
|
1164
|
+
return this.varMapByName.has(e) || this.boolVarMapByName.has(e);
|
|
1165
|
+
}
|
|
1166
|
+
getNextBoolVarName(e) {
|
|
1167
|
+
let t = this.boolVarPrefixCounters.get(e) ?? 0, n = `${e}_${t}`;
|
|
1168
|
+
for (; this.hasVarName(n);) t++, n = `${e}_${t}`;
|
|
1169
|
+
return this.boolVarPrefixCounters.set(e, t + 1), n;
|
|
1170
|
+
}
|
|
1171
|
+
createBoolVar(e) {
|
|
1172
|
+
let t = typeof e == "string" ? e.trim() : void 0, n = t && t.length > 0 ? t : this.getNextBoolVarName("p");
|
|
1173
|
+
if (this.hasVarName(n)) throw Error(`Variable with name '${n}' already exists in model`);
|
|
1174
|
+
let r = new f(n);
|
|
1175
|
+
return this.boolVars.push(r), this.boolVarMapByName.set(r.name, r), r;
|
|
1176
|
+
}
|
|
1177
|
+
addVar(e) {
|
|
1178
|
+
let t = e || {}, n = typeof t.name == "string" ? t.name.trim() : void 0, r = n && n.length > 0 ? n : void 0, i = new D({
|
|
1179
|
+
...t,
|
|
1180
|
+
name: r
|
|
1181
|
+
});
|
|
1182
|
+
if (this.hasVarName(i.name)) throw Error(`Variable with name '${i.name}' already exists in model`);
|
|
1183
|
+
return this.variables.push(i), this.varMapByName.set(i.name, i), i;
|
|
928
1184
|
}
|
|
929
1185
|
getVarByName(e) {
|
|
930
1186
|
return this.varMapByName.get(e);
|
|
931
1187
|
}
|
|
1188
|
+
getBoolVarByName(e) {
|
|
1189
|
+
return this.boolVarMapByName.get(e);
|
|
1190
|
+
}
|
|
932
1191
|
getConstraintByName(e) {
|
|
933
1192
|
return this.constrMapByName.get(e);
|
|
934
1193
|
}
|
|
935
1194
|
setObjective(e, t) {
|
|
936
|
-
|
|
1195
|
+
if (e instanceof b) throw Error("Cannot set objective to a constraint comparison (<=, >=, ==). Did you mean to use m.constrain(expr`... <= ...`)? For objectives, supply an unconstrained expression like expr`45 * ${x} + 80 * ${y}`.");
|
|
1196
|
+
t && (this.sense = l(t)), this.objective = typeof e == "string" ? M(e, (e) => this.getVarByName(e)) : typeof e == "number" ? new C(/* @__PURE__ */ new Map(), e) : e instanceof S || "terms" in e ? e.clone() : new C(/* @__PURE__ */ new Map([[e, 1]]), 0);
|
|
937
1197
|
}
|
|
938
1198
|
maximize(e) {
|
|
939
1199
|
this.setObjective(e, "Maximize");
|
|
@@ -941,12 +1201,30 @@ var Y = class {
|
|
|
941
1201
|
minimize(e) {
|
|
942
1202
|
this.setObjective(e, "Minimize");
|
|
943
1203
|
}
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
1204
|
+
constrain(e, t) {
|
|
1205
|
+
if (Array.isArray(e)) {
|
|
1206
|
+
for (let t of e) this.constrain(t);
|
|
1207
|
+
return this;
|
|
1208
|
+
}
|
|
1209
|
+
if (e instanceof S) throw Error("Cannot add a quadratic expression without a comparison operator (<=, >=, ==) as a constraint. Quadratic constraints are not supported (only linear constraints are allowed in MILP/LP/QP).");
|
|
1210
|
+
if (e instanceof C) throw Error("Cannot add a linear expression without a comparison operator (<=, >=, ==) as a constraint. Use expr`... <= ...` or .le(), .ge(), .eq().");
|
|
1211
|
+
return this.addConstraint(e, t), this;
|
|
1212
|
+
}
|
|
1213
|
+
getValues(e) {
|
|
1214
|
+
if (e == null) return null;
|
|
1215
|
+
if (e instanceof D || e instanceof f) return e.value;
|
|
1216
|
+
if (Array.isArray(e)) return e.map((e) => this.getValues(e));
|
|
1217
|
+
if (typeof e == "object") {
|
|
1218
|
+
let t = {};
|
|
1219
|
+
for (let [n, r] of Object.entries(e)) t[n] = this.getValues(r);
|
|
1220
|
+
return t;
|
|
1221
|
+
}
|
|
1222
|
+
return null;
|
|
947
1223
|
}
|
|
948
1224
|
addConstraint(e, t) {
|
|
949
|
-
if (e instanceof
|
|
1225
|
+
if (e instanceof S) throw Error("Cannot add a quadratic expression without a comparison operator (<=, >=, ==) as a constraint. Quadratic constraints are not supported (only linear constraints are allowed in MILP/LP/QP).");
|
|
1226
|
+
if (e instanceof C) throw Error("Cannot add a linear expression without a comparison operator (<=, >=, ==) as a constraint. Use expr`... <= ...` or .le(), .ge(), .eq().");
|
|
1227
|
+
if (e instanceof d) {
|
|
950
1228
|
let n = t || `lc_${this.logicalConstraints.length + 1}`;
|
|
951
1229
|
return this.logicalConstraints.push({
|
|
952
1230
|
name: n,
|
|
@@ -954,47 +1232,43 @@ var Y = class {
|
|
|
954
1232
|
}), e;
|
|
955
1233
|
}
|
|
956
1234
|
let n;
|
|
957
|
-
if (typeof e == "string" ? n =
|
|
1235
|
+
if (typeof e == "string" ? n = N(e, (e) => this.getVarByName(e), t) : (n = e, t && (n.name = t)), this.constrMapByName.has(n.name)) throw Error(`Constraint with name '${n.name}' already exists in model`);
|
|
958
1236
|
return this.constraints.push(n), this.constrMapByName.set(n.name, n), n;
|
|
959
1237
|
}
|
|
960
|
-
addConstr(e, t) {
|
|
961
|
-
return this.addConstraint(e, t);
|
|
962
|
-
}
|
|
963
|
-
addConstrs(e) {
|
|
964
|
-
return e.map((e) => this.addConstraint(e));
|
|
965
|
-
}
|
|
966
1238
|
add(e, t) {
|
|
967
1239
|
if (Array.isArray(e)) {
|
|
968
1240
|
for (let t of e) this.add(t);
|
|
969
1241
|
return this;
|
|
970
1242
|
}
|
|
971
|
-
return e instanceof
|
|
972
|
-
}
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
if (
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
1243
|
+
return e instanceof D ? (this.varMapByName.has(e.name) || (this.variables.push(e), this.varMapByName.set(e.name, e)), this) : (this.addConstraint(e, t), this);
|
|
1244
|
+
}
|
|
1245
|
+
indicator(e, t, n = {}) {
|
|
1246
|
+
if (t instanceof S) throw Error("Quadratic expressions or constraints are not supported in indicator constraints (only linear constraints are allowed).");
|
|
1247
|
+
if (!("sense" in t) || !("lhs" in t)) throw Error("Invalid constraint expression passed to indicator(). Expression must include a comparison operator (<=, >=, ==).");
|
|
1248
|
+
let r = t, i = n.activeValue === void 0 ? 1 : n.activeValue, a = n.M === void 0 ? 1e5 : n.M, o = n.name || `ind_${e.name}_${r.name}`, s = [], { lhs: c, sense: l, rhs: u } = r;
|
|
1249
|
+
if (i === 1) {
|
|
1250
|
+
if (l === "<=" || l === "==") {
|
|
1251
|
+
let t = this.addConstraint(c.add(e.mul(a)).le(u + a), l === "==" ? `${o}_le` : o);
|
|
1252
|
+
s.push(t);
|
|
979
1253
|
}
|
|
980
|
-
if (
|
|
981
|
-
let t = this.addConstraint(
|
|
982
|
-
|
|
1254
|
+
if (l === ">=" || l === "==") {
|
|
1255
|
+
let t = this.addConstraint(c.sub(e.mul(a)).ge(u - a), l === "==" ? `${o}_ge` : o);
|
|
1256
|
+
s.push(t);
|
|
983
1257
|
}
|
|
984
1258
|
} else {
|
|
985
|
-
if (
|
|
986
|
-
let t = this.addConstraint(
|
|
987
|
-
|
|
1259
|
+
if (l === "<=" || l === "==") {
|
|
1260
|
+
let t = this.addConstraint(c.sub(e.mul(a)).le(u), l === "==" ? `${o}_le` : o);
|
|
1261
|
+
s.push(t);
|
|
988
1262
|
}
|
|
989
|
-
if (
|
|
990
|
-
let t = this.addConstraint(
|
|
991
|
-
|
|
1263
|
+
if (l === ">=" || l === "==") {
|
|
1264
|
+
let t = this.addConstraint(c.add(e.mul(a)).ge(u), l === "==" ? `${o}_ge` : o);
|
|
1265
|
+
s.push(t);
|
|
992
1266
|
}
|
|
993
1267
|
}
|
|
994
|
-
return
|
|
1268
|
+
return s;
|
|
995
1269
|
}
|
|
996
1270
|
toLpString() {
|
|
997
|
-
let { lpString: e } =
|
|
1271
|
+
let { lpString: e } = R({
|
|
998
1272
|
name: this.name,
|
|
999
1273
|
sense: this.sense,
|
|
1000
1274
|
objective: this.objective,
|
|
@@ -1005,7 +1279,8 @@ var Y = class {
|
|
|
1005
1279
|
}
|
|
1006
1280
|
async optimize(e, t) {
|
|
1007
1281
|
let n, r;
|
|
1008
|
-
if (e && typeof e == "object" && "solve" in e && typeof e.solve == "function" ? (n = e, r = t || {}) : typeof e == "function" ? (n = new e(t), r = t || {}) : typeof e == "string" ? (n =
|
|
1282
|
+
if (e && typeof e == "object" && "solve" in e && typeof e.solve == "function" ? (n = e, r = t || {}) : typeof e == "function" ? (n = new e(t), r = t || {}) : typeof e == "string" ? (n = G(e, t), r = t || {}) : (r = { ...e }, r.solver ? (n = G(r.solver, r), delete r.solver) : n = this.solver || G()), this.objective instanceof S && this.objective.quadTerms.size > 0 && n.capabilities?.supportsQP === !1) throw Error(`Solver "${n.name}" does not support quadratic objectives (QP). Please use a QP-capable solver such as HiGHS or Clarabel.`);
|
|
1283
|
+
if (this.logicalConstraints.length > 0 && n.capabilities?.supportsSMT !== !0) throw Error(`Solver "${n.name}" does not support SMT / logical constraints (or, implies, not, xor). Please use an SMT-capable solver such as Z3.`);
|
|
1009
1284
|
let i = {
|
|
1010
1285
|
name: this.name,
|
|
1011
1286
|
sense: this.sense,
|
|
@@ -1014,13 +1289,23 @@ var Y = class {
|
|
|
1014
1289
|
variables: this.variables,
|
|
1015
1290
|
logicalConstraints: this.logicalConstraints,
|
|
1016
1291
|
boolVars: this.boolVars
|
|
1017
|
-
}, a =
|
|
1292
|
+
}, a = R(i), o = await n.solve(i, a, r);
|
|
1018
1293
|
this.runTime = o.runTime ?? 0, this.status = o.status, this.objectiveValue = o.objectiveValue ?? null;
|
|
1019
1294
|
let s = {}, c = {}, l = {}, u = {};
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1295
|
+
this.values.clear();
|
|
1296
|
+
for (let e of this.variables) e.value = null, e.reducedCost = null;
|
|
1297
|
+
for (let e of this.boolVars) e.value = null;
|
|
1298
|
+
for (let e of this.constraints) e.dual = null, e.slack = null;
|
|
1299
|
+
if (a?.nameToVar) for (let e of a.nameToVar.values()) e.value = null, e.reducedCost = null;
|
|
1300
|
+
if (a?.nameToConstraint) for (let e of a.nameToConstraint.values()) e.dual = null, e.slack = null;
|
|
1301
|
+
if (o.values && o.status !== "Infeasible" && o.status !== "Unbounded") {
|
|
1302
|
+
for (let [e, t] of Object.entries(o.values)) if (typeof t == "number" && !Number.isNaN(t)) {
|
|
1303
|
+
this.values.set(e, t);
|
|
1304
|
+
let n = this.getVarByName(e) || a.nameToVar.get(e);
|
|
1305
|
+
n && (n.value = t, s[n.name] = t);
|
|
1306
|
+
let r = this.boolVars.find((t) => t.name === e);
|
|
1307
|
+
r && (r.value = !!t);
|
|
1308
|
+
}
|
|
1024
1309
|
}
|
|
1025
1310
|
if (o.reducedCosts) for (let [e, t] of Object.entries(o.reducedCosts)) {
|
|
1026
1311
|
let n = this.getVarByName(e) || a.nameToVar.get(e);
|
|
@@ -1050,7 +1335,7 @@ var Y = class {
|
|
|
1050
1335
|
}
|
|
1051
1336
|
async check(e, t) {
|
|
1052
1337
|
let n, r;
|
|
1053
|
-
if (e && typeof e == "object" && "solve" in e && typeof e.solve == "function" ? (n = e, r = t || {}) : typeof e == "function" ? (n = new e(t), r = t || {}) : typeof e == "string" ? (n =
|
|
1338
|
+
if (e && typeof e == "object" && "solve" in e && typeof e.solve == "function" ? (n = e, r = t || {}) : typeof e == "function" ? (n = new e(t), r = t || {}) : typeof e == "string" ? (n = G(e, t), r = t || {}) : (r = { ...e }, r.solver ? (n = G(r.solver, r), delete r.solver) : n = this.solver || G()), this.logicalConstraints.length > 0 && n.capabilities?.supportsSMT !== !0) throw Error(`Solver "${n.name}" does not support SMT / logical constraints (or, implies, not, xor). Please use an SMT-capable solver such as Z3.`);
|
|
1054
1339
|
if (typeof n.check == "function") {
|
|
1055
1340
|
let e = await n.check({
|
|
1056
1341
|
name: this.name,
|
|
@@ -1059,21 +1344,26 @@ var Y = class {
|
|
|
1059
1344
|
constraints: this.constraints,
|
|
1060
1345
|
logicalConstraints: this.logicalConstraints
|
|
1061
1346
|
}, r);
|
|
1062
|
-
|
|
1063
|
-
|
|
1064
|
-
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1347
|
+
this.status = e.status, this.runTime = e.runTime ?? 0, this.unsatCore = e.unsatCore || [], this.values.clear();
|
|
1348
|
+
for (let e of this.variables) e.value = null;
|
|
1349
|
+
for (let e of this.boolVars) e.value = null;
|
|
1350
|
+
if (e.values && e.status === "Sat") for (let [t, n] of Object.entries(e.values)) {
|
|
1351
|
+
this.values.set(t, n);
|
|
1352
|
+
let e = this.getVarByName(t);
|
|
1353
|
+
e && typeof n == "number" && (e.value = n);
|
|
1354
|
+
let r = this.boolVars.find((e) => e.name === t);
|
|
1355
|
+
r && (r.value = !!n);
|
|
1069
1356
|
}
|
|
1070
1357
|
return e;
|
|
1071
1358
|
}
|
|
1072
1359
|
let i = this.objective, a = this.sense;
|
|
1073
1360
|
try {
|
|
1074
|
-
this.objective = new
|
|
1361
|
+
this.objective = new C(), this.sense = "Minimize";
|
|
1075
1362
|
let e = await this.optimize(n, r), t = e === "Optimal" || e === "Feasible", i = e === "Infeasible", a = {};
|
|
1076
|
-
|
|
1363
|
+
if (t) {
|
|
1364
|
+
for (let e of this.variables) e.value !== null && (a[e.name] = e.value);
|
|
1365
|
+
for (let e of this.boolVars) e.value !== null && (a[e.name] = e.value);
|
|
1366
|
+
}
|
|
1077
1367
|
return {
|
|
1078
1368
|
status: t ? "Sat" : i ? "Unsat" : "Unknown",
|
|
1079
1369
|
values: a,
|
|
@@ -1083,131 +1373,6 @@ var Y = class {
|
|
|
1083
1373
|
this.objective = i, this.sense = a;
|
|
1084
1374
|
}
|
|
1085
1375
|
}
|
|
1086
|
-
}, X = "Minimize", ce = "Maximize", le = "Continuous", ue = "Integer", de = "Binary", Z = {
|
|
1087
|
-
Optimal: "Optimal",
|
|
1088
|
-
Feasible: "Feasible",
|
|
1089
|
-
Infeasible: "Infeasible",
|
|
1090
|
-
Unbounded: "Unbounded",
|
|
1091
|
-
TimeLimit: "Not Solved (Time Limit)",
|
|
1092
|
-
IterationLimit: "Not Solved (Iteration Limit)",
|
|
1093
|
-
Error: "Error",
|
|
1094
|
-
NotSolved: "Not Solved",
|
|
1095
|
-
Sat: "Sat",
|
|
1096
|
-
Unsat: "Unsat",
|
|
1097
|
-
Unknown: "Unknown"
|
|
1098
|
-
}, fe = class e extends E {
|
|
1099
|
-
constructor(e, t, n, r = "Continuous") {
|
|
1100
|
-
super({
|
|
1101
|
-
name: e,
|
|
1102
|
-
lb: t === void 0 ? 0 : t,
|
|
1103
|
-
ub: n === void 0 ? Infinity : n,
|
|
1104
|
-
type: r
|
|
1105
|
-
});
|
|
1106
|
-
}
|
|
1107
|
-
static dicts(t, n, r, i, a = "Continuous") {
|
|
1108
|
-
let o = {};
|
|
1109
|
-
for (let s of n) {
|
|
1110
|
-
let n = `${t}_${s}`;
|
|
1111
|
-
o[s] = new e(n, r, i, a);
|
|
1112
|
-
}
|
|
1113
|
-
return o;
|
|
1114
|
-
}
|
|
1115
|
-
};
|
|
1116
|
-
function pe(e) {
|
|
1117
|
-
return e == null ? null : typeof e == "number" ? e : e.value;
|
|
1118
|
-
}
|
|
1119
|
-
var me = class {
|
|
1120
|
-
model;
|
|
1121
|
-
constructor(e = "NoName", t = X) {
|
|
1122
|
-
this.model = new Y({
|
|
1123
|
-
name: e,
|
|
1124
|
-
sense: t
|
|
1125
|
-
});
|
|
1126
|
-
}
|
|
1127
|
-
get name() {
|
|
1128
|
-
return this.model.name;
|
|
1129
|
-
}
|
|
1130
|
-
get sense() {
|
|
1131
|
-
return this.model.sense;
|
|
1132
|
-
}
|
|
1133
|
-
set sense(e) {
|
|
1134
|
-
this.model.sense = e;
|
|
1135
|
-
}
|
|
1136
|
-
get objective() {
|
|
1137
|
-
return this.model.objective;
|
|
1138
|
-
}
|
|
1139
|
-
get variables() {
|
|
1140
|
-
return this.model.variables;
|
|
1141
|
-
}
|
|
1142
|
-
get constraints() {
|
|
1143
|
-
return this.model.constraints;
|
|
1144
|
-
}
|
|
1145
|
-
get status() {
|
|
1146
|
-
return this.model.status;
|
|
1147
|
-
}
|
|
1148
|
-
get objectiveValue() {
|
|
1149
|
-
return this.model.objectiveValue;
|
|
1150
|
-
}
|
|
1151
|
-
addVariable(e) {
|
|
1152
|
-
return this.model.getVarByName(e.name) || (this.model.variables.push(e), this.model.varMapByName.set(e.name, e)), e;
|
|
1153
|
-
}
|
|
1154
|
-
setObjective(e) {
|
|
1155
|
-
if (typeof e == "object" && e) {
|
|
1156
|
-
if ("terms" in e) for (let [t] of e.terms) this.addVariable(t);
|
|
1157
|
-
else e instanceof E && this.addVariable(e);
|
|
1158
|
-
}
|
|
1159
|
-
this.model.setObjective(e);
|
|
1160
|
-
}
|
|
1161
|
-
addConstraint(e, t) {
|
|
1162
|
-
if (typeof e == "object" && e && "lhs" in e) for (let [t] of e.lhs.terms) this.addVariable(t);
|
|
1163
|
-
return this.model.addConstraint(e, t);
|
|
1164
|
-
}
|
|
1165
|
-
add(e, t) {
|
|
1166
|
-
typeof e == "string" ? /(<=|>=|==|=<|=>|=)/.test(e) ? this.addConstraint(e, t) : this.setObjective(e) : e instanceof v ? this.addConstraint(e, t) : this.setObjective(e);
|
|
1167
|
-
}
|
|
1168
|
-
async solve(e, t) {
|
|
1169
|
-
return this.model.optimize(e, t);
|
|
1170
|
-
}
|
|
1171
|
-
toLpString() {
|
|
1172
|
-
return this.model.toLpString();
|
|
1173
|
-
}
|
|
1174
|
-
}, Q = "Minimize", $ = "Maximize", he = "Binary", ge = "Integer", _e = "Continuous";
|
|
1175
|
-
function ve(e) {
|
|
1176
|
-
return {
|
|
1177
|
-
expr: e,
|
|
1178
|
-
sense: $
|
|
1179
|
-
};
|
|
1180
|
-
}
|
|
1181
|
-
function ye(e) {
|
|
1182
|
-
return {
|
|
1183
|
-
expr: e,
|
|
1184
|
-
sense: Q
|
|
1185
|
-
};
|
|
1186
|
-
}
|
|
1187
|
-
var be = class extends Y {
|
|
1188
|
-
constructor(e = "MipModel", t = Q) {
|
|
1189
|
-
super({
|
|
1190
|
-
name: e,
|
|
1191
|
-
sense: t
|
|
1192
|
-
});
|
|
1193
|
-
}
|
|
1194
|
-
add_var(e = {}) {
|
|
1195
|
-
return this.addVar({
|
|
1196
|
-
name: e.name,
|
|
1197
|
-
type: e.var_type,
|
|
1198
|
-
lb: e.lb,
|
|
1199
|
-
ub: e.ub
|
|
1200
|
-
});
|
|
1201
|
-
}
|
|
1202
|
-
set objective_spec(e) {
|
|
1203
|
-
this.setObjective(e.expr, e.sense);
|
|
1204
|
-
}
|
|
1205
|
-
get objective_value() {
|
|
1206
|
-
return this.objectiveValue;
|
|
1207
|
-
}
|
|
1208
|
-
add_constr(e, t) {
|
|
1209
|
-
return this.addConstraint(e, t);
|
|
1210
|
-
}
|
|
1211
1376
|
};
|
|
1212
1377
|
//#endregion
|
|
1213
|
-
export {
|
|
1378
|
+
export { d as BoolExpr, p as BoolOp, f as BoolVar, b as Constraint, ie as HiGHS, Q as HighsSolver, C as LinExpr, $ as MockSolver, se as Model, c as OFFICIAL_HIGHS_CDN_WASM_URL, S as QuadExpr, D as Var, m as and, F as c, ee as dot, I as expr, R as generateLpString, i as getHighs, o as getHighsWasmUrl, G as getSolver, _ as implies, n as isValidWasmHeader, K as listAvailableSolvers, l as normalizeSense, g as not, h as or, N as parseConstraint, M as parseExpr, e as probeWasmUrl, U as registerSolver, a as resolveBrowserWasmUrl, W as setDefaultSolver, s as setHighsWasmUrl, t as solveLpWithHighs, w as sum, v as xor };
|