diff-grok 1.0.10 → 1.1.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/.claude/settings.local.json +11 -0
- package/CLAUDE.md +98 -0
- package/README.MD +100 -24
- package/images/E5.png +0 -0
- package/images/HIRES.png +0 -0
- package/images/OREGO.png +0 -0
- package/images/POLL-full.png +0 -0
- package/images/ROBER.png +0 -0
- package/images/VDP0L.png +0 -0
- package/index.js +1 -1
- package/index.js.map +1 -1
- package/index.ts +2 -1
- package/jest.config.js +1 -0
- package/package.json +1 -1
- package/src/examples/bioreactor.js +125 -0
- package/src/examples/bioreactor.js.map +1 -0
- package/src/examples/bioreactor.ts +132 -0
- package/src/examples/cyclic-model.js +3 -1
- package/src/examples/cyclic-model.js.map +1 -1
- package/src/examples/cyclic-model.ts +3 -1
- package/src/solver-tools/ab4-method.js +332 -0
- package/src/solver-tools/ab4-method.js.map +1 -0
- package/src/solver-tools/ab4-method.ts +395 -0
- package/src/solver-tools/ab5-method.js +334 -0
- package/src/solver-tools/ab5-method.js.map +1 -0
- package/src/solver-tools/ab5-method.ts +397 -0
- package/src/solver-tools/index.js +6 -0
- package/src/solver-tools/index.js.map +1 -1
- package/src/solver-tools/index.ts +6 -0
- package/src/solver-tools/lsoda/blas.js +246 -0
- package/src/solver-tools/lsoda/blas.js.map +1 -0
- package/src/solver-tools/lsoda/blas.ts +267 -0
- package/src/solver-tools/lsoda/cfode.js +73 -0
- package/src/solver-tools/lsoda/cfode.js.map +1 -0
- package/src/solver-tools/lsoda/cfode.ts +83 -0
- package/src/solver-tools/lsoda/common.js +94 -0
- package/src/solver-tools/lsoda/common.js.map +1 -0
- package/src/solver-tools/lsoda/common.ts +135 -0
- package/src/solver-tools/lsoda/corfailure.js +25 -0
- package/src/solver-tools/lsoda/corfailure.js.map +1 -0
- package/src/solver-tools/lsoda/corfailure.ts +30 -0
- package/src/solver-tools/lsoda/correction.js +101 -0
- package/src/solver-tools/lsoda/correction.js.map +1 -0
- package/src/solver-tools/lsoda/correction.ts +119 -0
- package/src/solver-tools/lsoda/dense.js +110 -0
- package/src/solver-tools/lsoda/dense.js.map +1 -0
- package/src/solver-tools/lsoda/dense.ts +129 -0
- package/src/solver-tools/lsoda/index.js +4 -0
- package/src/solver-tools/lsoda/index.js.map +1 -0
- package/src/solver-tools/lsoda/index.ts +5 -0
- package/src/solver-tools/lsoda/intdy.js +43 -0
- package/src/solver-tools/lsoda/intdy.js.map +1 -0
- package/src/solver-tools/lsoda/intdy.ts +50 -0
- package/src/solver-tools/lsoda/lsoda.js +567 -0
- package/src/solver-tools/lsoda/lsoda.js.map +1 -0
- package/src/solver-tools/lsoda/lsoda.ts +632 -0
- package/src/solver-tools/lsoda/methodswitch.js +97 -0
- package/src/solver-tools/lsoda/methodswitch.js.map +1 -0
- package/src/solver-tools/lsoda/methodswitch.ts +107 -0
- package/src/solver-tools/lsoda/orderswitch.js +86 -0
- package/src/solver-tools/lsoda/orderswitch.js.map +1 -0
- package/src/solver-tools/lsoda/orderswitch.ts +95 -0
- package/src/solver-tools/lsoda/prja.js +43 -0
- package/src/solver-tools/lsoda/prja.js.map +1 -0
- package/src/solver-tools/lsoda/prja.ts +49 -0
- package/src/solver-tools/lsoda/scaleh.js +30 -0
- package/src/solver-tools/lsoda/scaleh.js.map +1 -0
- package/src/solver-tools/lsoda/scaleh.ts +33 -0
- package/src/solver-tools/lsoda/solsy.js +14 -0
- package/src/solver-tools/lsoda/solsy.js.map +1 -0
- package/src/solver-tools/lsoda/solsy.ts +18 -0
- package/src/solver-tools/lsoda/stoda.js +259 -0
- package/src/solver-tools/lsoda/stoda.js.map +1 -0
- package/src/solver-tools/lsoda/stoda.ts +286 -0
- package/src/solver-tools/lsoda-method.js +120 -0
- package/src/solver-tools/lsoda-method.js.map +1 -0
- package/src/solver-tools/lsoda-method.ts +136 -0
- package/src/solver-tools/mrt-method.js +81 -18
- package/src/solver-tools/mrt-method.js.map +1 -1
- package/src/solver-tools/mrt-method.ts +111 -21
- package/src/solver-tools/rk3-method.js +210 -0
- package/src/solver-tools/rk3-method.js.map +1 -0
- package/src/solver-tools/rk3-method.ts +257 -0
- package/src/solver-tools/rk4-method.js +236 -0
- package/src/solver-tools/rk4-method.js.map +1 -0
- package/src/solver-tools/rk4-method.ts +286 -0
- package/src/solver-tools/rkdp-method.js +247 -0
- package/src/solver-tools/rkdp-method.js.map +1 -0
- package/src/solver-tools/rkdp-method.ts +300 -0
- package/src/solver-tools/ros34prw-method.js +1 -1
- package/src/solver-tools/ros34prw-method.js.map +1 -1
- package/src/solver-tools/ros34prw-method.ts +1 -1
- package/src/solver-tools/ros3prw-method.js +1 -1
- package/src/solver-tools/ros3prw-method.js.map +1 -1
- package/src/solver-tools/ros3prw-method.ts +1 -1
- package/src/solver-tools/solver-defs.js +6 -0
- package/src/solver-tools/solver-defs.js.map +1 -1
- package/src/solver-tools/solver-defs.ts +6 -0
- package/src/tests/correctness.test.js +6 -4
- package/src/tests/correctness.test.js.map +1 -1
- package/src/tests/correctness.test.ts +6 -4
- package/src/tests/lsoda-lib-correctness.test.js +223 -0
- package/src/tests/lsoda-lib-correctness.test.js.map +1 -0
- package/src/tests/lsoda-lib-correctness.test.ts +283 -0
- package/src/tests/lsoda-lib-performance.test.js +95 -0
- package/src/tests/lsoda-lib-performance.test.js.map +1 -0
- package/src/tests/lsoda-lib-performance.test.ts +126 -0
- package/src/tests/performance.test.js +10 -8
- package/src/tests/performance.test.js.map +1 -1
- package/src/tests/performance.test.ts +10 -8
- package/src/tests/test-defs.js +14 -1
- package/src/tests/test-defs.js.map +1 -1
- package/src/tests/test-defs.ts +15 -1
- package/src/worker-tools/solving.js +13 -1
- package/src/worker-tools/solving.js.map +1 -1
- package/src/worker-tools/solving.ts +20 -1
- package/docs/.nojekyll +0 -1
- package/docs/assets/hierarchy.js +0 -1
- package/docs/assets/highlight.css +0 -99
- package/docs/assets/icons.js +0 -18
- package/docs/assets/icons.svg +0 -1
- package/docs/assets/main.js +0 -60
- package/docs/assets/navigation.js +0 -1
- package/docs/assets/search.js +0 -1
- package/docs/assets/style.css +0 -1633
- package/docs/classes/BasicModelPipelineCreator.html +0 -10
- package/docs/classes/Callback.html +0 -7
- package/docs/classes/CyclicModelPipelineCreator.html +0 -10
- package/docs/classes/IterCheckerCallback.html +0 -8
- package/docs/classes/PipelineCreator.html +0 -6
- package/docs/classes/TimeCheckerCallback.html +0 -8
- package/docs/classes/UpdatesModelPipelineCreator.html +0 -10
- package/docs/functions/applyPipeline.html +0 -9
- package/docs/functions/getCallback.html +0 -3
- package/docs/functions/getIVP.html +0 -6
- package/docs/functions/getInputVector.html +0 -2
- package/docs/functions/getIvp2WebWorker.html +0 -6
- package/docs/functions/getJScode.html +0 -6
- package/docs/functions/getOutputNames.html +0 -4
- package/docs/functions/getPipelineCreator.html +0 -7
- package/docs/functions/mrt.html +0 -11
- package/docs/functions/printE5.html +0 -76
- package/docs/functions/printHires.html +0 -76
- package/docs/functions/printOrego.html +0 -66
- package/docs/functions/printPollution.html +0 -163
- package/docs/functions/printRobertson.html +0 -60
- package/docs/functions/printVdpol.html +0 -66
- package/docs/functions/ros34prw.html +0 -8
- package/docs/functions/ros3prw.html +0 -8
- package/docs/functions/solveIvp.html +0 -5
- package/docs/hierarchy.html +0 -1
- package/docs/index.html +0 -683
- package/docs/media/CONTRIBUTING.md +0 -74
- package/docs/media/POLL.png +0 -0
- package/docs/media/VDPOL.png +0 -0
- package/docs/media/acid-prod.gif +0 -0
- package/docs/media/basic-use.js +0 -40
- package/docs/media/basic-use.js.map +0 -1
- package/docs/media/basic-use.ts +0 -44
- package/docs/media/check-methods.js +0 -59
- package/docs/media/check-methods.js.map +0 -1
- package/docs/media/check-methods.ts +0 -81
- package/docs/media/corr-probs.js +0 -132
- package/docs/media/corr-probs.js.map +0 -1
- package/docs/media/corr-probs.ts +0 -155
- package/docs/media/cyclic-model.js +0 -100
- package/docs/media/cyclic-model.js.map +0 -1
- package/docs/media/cyclic-model.ts +0 -110
- package/docs/media/e5.js +0 -36
- package/docs/media/e5.js.map +0 -1
- package/docs/media/e5.ts +0 -36
- package/docs/media/hires.js +0 -39
- package/docs/media/hires.js.map +0 -1
- package/docs/media/hires.ts +0 -40
- package/docs/media/model-updates.js +0 -112
- package/docs/media/model-updates.js.map +0 -1
- package/docs/media/model-updates.ts +0 -122
- package/docs/media/orego.js +0 -24
- package/docs/media/orego.js.map +0 -1
- package/docs/media/orego.ts +0 -25
- package/docs/media/pipeline-use.js +0 -87
- package/docs/media/pipeline-use.js.map +0 -1
- package/docs/media/pipeline-use.ts +0 -98
- package/docs/media/pollution.js +0 -132
- package/docs/media/pollution.js.map +0 -1
- package/docs/media/pollution.ts +0 -133
- package/docs/media/print-benchmark.js +0 -581
- package/docs/media/print-benchmark.js.map +0 -1
- package/docs/media/print-benchmark.ts +0 -594
- package/docs/media/robertson.js +0 -19
- package/docs/media/robertson.js.map +0 -1
- package/docs/media/robertson.ts +0 -19
- package/docs/media/scripting.js +0 -30
- package/docs/media/scripting.js.map +0 -1
- package/docs/media/scripting.ts +0 -35
- package/docs/media/vdpol.js +0 -17
- package/docs/media/vdpol.js.map +0 -1
- package/docs/media/vdpol.ts +0 -17
- package/docs/modules.html +0 -1
- package/docs/types/Arg.html +0 -12
- package/docs/types/DifEqs.html +0 -8
- package/docs/types/Func.html +0 -7
- package/docs/types/IVP.html +0 -40
- package/docs/types/IVP2WebWorker.html +0 -12
- package/docs/types/Input.html +0 -8
- package/docs/types/Loop.html +0 -7
- package/docs/types/ODEs.html +0 -31
- package/docs/types/Output.html +0 -6
- package/docs/types/Pipeline.html +0 -6
- package/docs/types/SolverOptions.html +0 -8
- package/docs/types/Update.html +0 -9
- package/docs/types/Wrapper.html +0 -8
|
@@ -0,0 +1,267 @@
|
|
|
1
|
+
// BLAS linear algebra routines
|
|
2
|
+
// All arrays are 1-indexed (element [0] unused), matching the C/Fortran convention.
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Compute dy = da * dx + dy
|
|
6
|
+
* Arrays are 1-indexed with stride incx/incy.
|
|
7
|
+
*/
|
|
8
|
+
export function daxpy(
|
|
9
|
+
n: number, da: number, dx: Float64Array, incx: number,
|
|
10
|
+
dy: Float64Array, incy: number,
|
|
11
|
+
): void {
|
|
12
|
+
if (n < 0 || da === 0.) return;
|
|
13
|
+
|
|
14
|
+
if (incx !== incy || incx < 1) {
|
|
15
|
+
let ix = 1;
|
|
16
|
+
let iy = 1;
|
|
17
|
+
if (incx < 0) ix = (-n + 1) * incx + 1;
|
|
18
|
+
if (incy < 0) iy = (-n + 1) * incy + 1;
|
|
19
|
+
for (let i = 1; i <= n; i++) {
|
|
20
|
+
dy[iy] = dy[iy] + da * dx[ix];
|
|
21
|
+
ix += incx;
|
|
22
|
+
iy += incy;
|
|
23
|
+
}
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
if (incx === 1) {
|
|
28
|
+
const m = n % 4;
|
|
29
|
+
if (m !== 0) {
|
|
30
|
+
for (let i = 1; i <= m; i++)
|
|
31
|
+
dy[i] = dy[i] + da * dx[i];
|
|
32
|
+
if (n < 4) return;
|
|
33
|
+
}
|
|
34
|
+
for (let i = m + 1; i <= n; i += 4) {
|
|
35
|
+
dy[i] = dy[i] + da * dx[i];
|
|
36
|
+
dy[i + 1] = dy[i + 1] + da * dx[i + 1];
|
|
37
|
+
dy[i + 2] = dy[i + 2] + da * dx[i + 2];
|
|
38
|
+
dy[i + 3] = dy[i + 3] + da * dx[i + 3];
|
|
39
|
+
}
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
for (let i = 1; i <= n * incx; i += incx)
|
|
44
|
+
dy[i] = da * dx[i] + dy[i];
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* Compute dot product dx . dy
|
|
49
|
+
* Arrays are 1-indexed with stride incx/incy.
|
|
50
|
+
*/
|
|
51
|
+
export function ddot(
|
|
52
|
+
n: number, dx: Float64Array, incx: number,
|
|
53
|
+
dy: Float64Array, incy: number,
|
|
54
|
+
): number {
|
|
55
|
+
let dotprod = 0.;
|
|
56
|
+
if (n <= 0) return dotprod;
|
|
57
|
+
|
|
58
|
+
if (incx !== incy || incx < 1) {
|
|
59
|
+
let ix = 1;
|
|
60
|
+
let iy = 1;
|
|
61
|
+
if (incx < 0) ix = (-n + 1) * incx + 1;
|
|
62
|
+
if (incy < 0) iy = (-n + 1) * incy + 1;
|
|
63
|
+
for (let i = 1; i <= n; i++) {
|
|
64
|
+
dotprod += dx[ix] * dy[iy];
|
|
65
|
+
ix += incx;
|
|
66
|
+
iy += incy;
|
|
67
|
+
}
|
|
68
|
+
return dotprod;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
if (incx === 1) {
|
|
72
|
+
for (let i = 1; i <= n; i++)
|
|
73
|
+
dotprod += dx[i] * dy[i];
|
|
74
|
+
return dotprod;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
for (let i = 1; i <= n * incx; i += incx)
|
|
78
|
+
dotprod += dx[i] * dy[i];
|
|
79
|
+
return dotprod;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
/**
|
|
83
|
+
* Scale vector: dx = da * dx
|
|
84
|
+
* Array is 1-indexed with stride incx.
|
|
85
|
+
*/
|
|
86
|
+
export function dscal(n: number, da: number, dx: Float64Array, incx: number): void {
|
|
87
|
+
if (n <= 0) return;
|
|
88
|
+
|
|
89
|
+
if (incx !== 1) {
|
|
90
|
+
for (let i = 1; i <= n * incx; i += incx)
|
|
91
|
+
dx[i] = da * dx[i];
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
const m = n % 5;
|
|
96
|
+
if (m !== 0) {
|
|
97
|
+
for (let i = 1; i <= m; i++)
|
|
98
|
+
dx[i] = da * dx[i];
|
|
99
|
+
if (n < 5) return;
|
|
100
|
+
}
|
|
101
|
+
for (let i = m + 1; i <= n; i += 5) {
|
|
102
|
+
dx[i] = da * dx[i];
|
|
103
|
+
dx[i + 1] = da * dx[i + 1];
|
|
104
|
+
dx[i + 2] = da * dx[i + 2];
|
|
105
|
+
dx[i + 3] = da * dx[i + 3];
|
|
106
|
+
dx[i + 4] = da * dx[i + 4];
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
/**
|
|
111
|
+
* Find index of element with maximum absolute value.
|
|
112
|
+
* Array is 1-indexed. Returns 1-based index (0 if n <= 0).
|
|
113
|
+
*/
|
|
114
|
+
export function idamax(n: number, dx: Float64Array, incx: number): number {
|
|
115
|
+
let xindex = 0;
|
|
116
|
+
if (n <= 0) return xindex;
|
|
117
|
+
xindex = 1;
|
|
118
|
+
if (n <= 1 || incx <= 0) return xindex;
|
|
119
|
+
|
|
120
|
+
if (incx !== 1) {
|
|
121
|
+
let dmax = Math.abs(dx[1]);
|
|
122
|
+
let ii = 2;
|
|
123
|
+
for (let i = 1 + incx; i <= n * incx; i += incx) {
|
|
124
|
+
const xmag = Math.abs(dx[i]);
|
|
125
|
+
if (xmag > dmax) {
|
|
126
|
+
xindex = ii;
|
|
127
|
+
dmax = xmag;
|
|
128
|
+
}
|
|
129
|
+
ii++;
|
|
130
|
+
}
|
|
131
|
+
return xindex;
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
let dmax = Math.abs(dx[1]);
|
|
135
|
+
for (let i = 2; i <= n; i++) {
|
|
136
|
+
const xmag = Math.abs(dx[i]);
|
|
137
|
+
if (xmag > dmax) {
|
|
138
|
+
xindex = i;
|
|
139
|
+
dmax = xmag;
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
return xindex;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* LU factorization by Gaussian elimination with partial pivoting.
|
|
147
|
+
* a: 2D matrix (a[i][j], 1-indexed rows and columns)
|
|
148
|
+
* n: matrix dimension
|
|
149
|
+
* ipvt: pivot indices output (1-indexed)
|
|
150
|
+
* Returns info: 0 = normal, k = U[k][k] == 0 (singular).
|
|
151
|
+
*/
|
|
152
|
+
export function dgefa(a: Float64Array[], n: number, ipvt: Int32Array): number {
|
|
153
|
+
let info = 0;
|
|
154
|
+
|
|
155
|
+
for (let k = 1; k <= n - 1; k++) {
|
|
156
|
+
// Find pivot index. a[k] + k - 1 in C => subarray from index k
|
|
157
|
+
const j = idamax(n - k + 1, a[k].subarray(k - 1), 1) + k - 1;
|
|
158
|
+
ipvt[k] = j;
|
|
159
|
+
|
|
160
|
+
if (a[k][j] === 0.) {
|
|
161
|
+
info = k;
|
|
162
|
+
continue;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
// Interchange if necessary
|
|
166
|
+
if (j !== k) {
|
|
167
|
+
const t = a[k][j];
|
|
168
|
+
a[k][j] = a[k][k];
|
|
169
|
+
a[k][k] = t;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
// Compute multipliers
|
|
173
|
+
const t = -1. / a[k][k];
|
|
174
|
+
dscal(n - k, t, a[k].subarray(k), 1);
|
|
175
|
+
|
|
176
|
+
// Column elimination with row indexing
|
|
177
|
+
for (let i = k + 1; i <= n; i++) {
|
|
178
|
+
const t2 = a[i][j];
|
|
179
|
+
if (j !== k) {
|
|
180
|
+
a[i][j] = a[i][k];
|
|
181
|
+
a[i][k] = t2;
|
|
182
|
+
}
|
|
183
|
+
daxpy(n - k, t2, a[k].subarray(k), 1, a[i].subarray(k), 1);
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
ipvt[n] = n;
|
|
188
|
+
if (a[n][n] === 0.) info = n;
|
|
189
|
+
return info;
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
/**
|
|
193
|
+
* Solve linear system using LU factors from dgefa.
|
|
194
|
+
* a: LU factored matrix (1-indexed)
|
|
195
|
+
* n: dimension
|
|
196
|
+
* ipvt: pivot indices (1-indexed)
|
|
197
|
+
* b: right-hand side on input, solution on output (1-indexed)
|
|
198
|
+
* job: 0 = solve A*x=b, nonzero = solve A^T*x=b
|
|
199
|
+
*/
|
|
200
|
+
export function dgesl(
|
|
201
|
+
a: Float64Array[], n: number, ipvt: Int32Array,
|
|
202
|
+
b: Float64Array, job: number,
|
|
203
|
+
): void {
|
|
204
|
+
if (job === 0) {
|
|
205
|
+
// Solve L * y = b
|
|
206
|
+
for (let k = 1; k <= n; k++) {
|
|
207
|
+
const t = ddot(k - 1, a[k], 1, b, 1);
|
|
208
|
+
b[k] = (b[k] - t) / a[k][k];
|
|
209
|
+
}
|
|
210
|
+
// Solve U * x = y
|
|
211
|
+
for (let k = n - 1; k >= 1; k--) {
|
|
212
|
+
b[k] = b[k] + ddot(n - k, a[k].subarray(k), 1, b.subarray(k), 1);
|
|
213
|
+
const j = ipvt[k];
|
|
214
|
+
if (j !== k) {
|
|
215
|
+
const t = b[j];
|
|
216
|
+
b[j] = b[k];
|
|
217
|
+
b[k] = t;
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
return;
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
// Solve Transpose(U) * y = b
|
|
224
|
+
for (let k = 1; k <= n - 1; k++) {
|
|
225
|
+
const j = ipvt[k];
|
|
226
|
+
const t = b[j];
|
|
227
|
+
if (j !== k) {
|
|
228
|
+
b[j] = b[k];
|
|
229
|
+
b[k] = t;
|
|
230
|
+
}
|
|
231
|
+
daxpy(n - k, t, a[k].subarray(k), 1, b.subarray(k), 1);
|
|
232
|
+
}
|
|
233
|
+
// Solve Transpose(L) * x = y
|
|
234
|
+
for (let k = n; k >= 1; k--) {
|
|
235
|
+
b[k] = b[k] / a[k][k];
|
|
236
|
+
const t = -b[k];
|
|
237
|
+
daxpy(k - 1, t, a[k], 1, b, 1);
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
/**
|
|
242
|
+
* Weighted max-norm: max(i=1..n) |v[i]| * w[i]
|
|
243
|
+
* Arrays are 1-indexed.
|
|
244
|
+
*/
|
|
245
|
+
export function vmnorm(n: number, v: Float64Array, w: Float64Array): number {
|
|
246
|
+
let vm = 0.;
|
|
247
|
+
for (let i = 1; i <= n; i++)
|
|
248
|
+
vm = Math.max(vm, Math.abs(v[i]) * w[i]);
|
|
249
|
+
return vm;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
/**
|
|
253
|
+
* Weighted matrix norm consistent with vmnorm.
|
|
254
|
+
* fnorm = max(i=1..n) ( w[i] * sum(j=1..n) |a[i][j]| / w[j] )
|
|
255
|
+
* a is 2D (1-indexed), w is 1-indexed.
|
|
256
|
+
*/
|
|
257
|
+
export function fnorm(n: number, a: Float64Array[], w: Float64Array): number {
|
|
258
|
+
let an = 0.;
|
|
259
|
+
for (let i = 1; i <= n; i++) {
|
|
260
|
+
let sum = 0.;
|
|
261
|
+
const ap1 = a[i];
|
|
262
|
+
for (let j = 1; j <= n; j++)
|
|
263
|
+
sum += Math.abs(ap1[j]) / w[j];
|
|
264
|
+
an = Math.max(an, sum * w[i]);
|
|
265
|
+
}
|
|
266
|
+
return an;
|
|
267
|
+
}
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Set coefficients for the current method.
|
|
3
|
+
* Computes elco and tesco arrays for all orders.
|
|
4
|
+
* meth=1: Adams (orders 1-12), meth=2: BDF (orders 1-5).
|
|
5
|
+
*/
|
|
6
|
+
export function cfode(ctx, meth) {
|
|
7
|
+
const c = ctx.common;
|
|
8
|
+
const pc = new Float64Array(13);
|
|
9
|
+
if (meth === 1) {
|
|
10
|
+
c.elco[1][1] = 1.;
|
|
11
|
+
c.elco[1][2] = 1.;
|
|
12
|
+
c.tesco[1][1] = 0.;
|
|
13
|
+
c.tesco[1][2] = 2.;
|
|
14
|
+
c.tesco[2][1] = 1.;
|
|
15
|
+
c.tesco[12][3] = 0.;
|
|
16
|
+
pc[1] = 1.;
|
|
17
|
+
let rqfac = 1.;
|
|
18
|
+
for (let nq = 2; nq <= 12; nq++) {
|
|
19
|
+
const rq1fac = rqfac;
|
|
20
|
+
rqfac = rqfac / nq;
|
|
21
|
+
const nqm1 = nq - 1;
|
|
22
|
+
const fnqm1 = nqm1;
|
|
23
|
+
const nqp1 = nq + 1;
|
|
24
|
+
// Form coefficients of p(x)*(x+nq-1)
|
|
25
|
+
pc[nq] = 0.;
|
|
26
|
+
for (let i = nq; i >= 2; i--)
|
|
27
|
+
pc[i] = pc[i - 1] + fnqm1 * pc[i];
|
|
28
|
+
pc[1] = fnqm1 * pc[1];
|
|
29
|
+
// Compute integral, -1 to 0, of p(x) and x*p(x)
|
|
30
|
+
let pint = pc[1];
|
|
31
|
+
let xpin = pc[1] / 2.;
|
|
32
|
+
let tsign = 1.;
|
|
33
|
+
for (let i = 2; i <= nq; i++) {
|
|
34
|
+
tsign = -tsign;
|
|
35
|
+
pint += tsign * pc[i] / i;
|
|
36
|
+
xpin += tsign * pc[i] / (i + 1);
|
|
37
|
+
}
|
|
38
|
+
// Store coefficients in elco and tesco
|
|
39
|
+
c.elco[nq][1] = pint * rq1fac;
|
|
40
|
+
c.elco[nq][2] = 1.;
|
|
41
|
+
for (let i = 2; i <= nq; i++)
|
|
42
|
+
c.elco[nq][i + 1] = rq1fac * pc[i] / i;
|
|
43
|
+
const agamq = rqfac * xpin;
|
|
44
|
+
const ragq = 1. / agamq;
|
|
45
|
+
c.tesco[nq][2] = ragq;
|
|
46
|
+
if (nq < 12)
|
|
47
|
+
c.tesco[nqp1][1] = ragq * rqfac / nqp1;
|
|
48
|
+
c.tesco[nqm1][3] = ragq;
|
|
49
|
+
}
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
// meth = 2 (BDF)
|
|
53
|
+
pc[1] = 1.;
|
|
54
|
+
let rq1fac = 1.;
|
|
55
|
+
for (let nq = 1; nq <= 5; nq++) {
|
|
56
|
+
const fnq = nq;
|
|
57
|
+
const nqp1 = nq + 1;
|
|
58
|
+
// Form coefficients of p(x)*(x+nq)
|
|
59
|
+
pc[nqp1] = 0.;
|
|
60
|
+
for (let i = nq + 1; i >= 2; i--)
|
|
61
|
+
pc[i] = pc[i - 1] + fnq * pc[i];
|
|
62
|
+
pc[1] *= fnq;
|
|
63
|
+
// Store coefficients in elco and tesco
|
|
64
|
+
for (let i = 1; i <= nqp1; i++)
|
|
65
|
+
c.elco[nq][i] = pc[i] / pc[2];
|
|
66
|
+
c.elco[nq][2] = 1.;
|
|
67
|
+
c.tesco[nq][1] = rq1fac;
|
|
68
|
+
c.tesco[nq][2] = nqp1 / c.elco[nq][1];
|
|
69
|
+
c.tesco[nq][3] = (nq + 2) / c.elco[nq][1];
|
|
70
|
+
rq1fac /= fnq;
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
//# sourceMappingURL=cfode.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cfode.js","sourceRoot":"","sources":["cfode.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AACH,MAAM,UAAU,KAAK,CAAC,GAAiB,EAAE,IAAY;IACnD,MAAM,CAAC,GAAG,GAAG,CAAC,MAAO,CAAC;IACtB,MAAM,EAAE,GAAG,IAAI,YAAY,CAAC,EAAE,CAAC,CAAC;IAEhC,IAAI,IAAI,KAAK,CAAC,EAAE,CAAC;QACf,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QAClB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QAClB,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACnB,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACnB,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACnB,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACpB,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACX,IAAI,KAAK,GAAG,EAAE,CAAC;QAEf,KAAK,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,IAAI,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC;YAChC,MAAM,MAAM,GAAG,KAAK,CAAC;YACrB,KAAK,GAAG,KAAK,GAAG,EAAE,CAAC;YACnB,MAAM,IAAI,GAAG,EAAE,GAAG,CAAC,CAAC;YACpB,MAAM,KAAK,GAAG,IAAI,CAAC;YACnB,MAAM,IAAI,GAAG,EAAE,GAAG,CAAC,CAAC;YAEpB,qCAAqC;YACrC,EAAE,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC;YACZ,KAAK,IAAI,CAAC,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE;gBAC1B,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,KAAK,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;YACpC,EAAE,CAAC,CAAC,CAAC,GAAG,KAAK,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;YAEtB,gDAAgD;YAChD,IAAI,IAAI,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;YACjB,IAAI,IAAI,GAAG,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;YACtB,IAAI,KAAK,GAAG,EAAE,CAAC;YACf,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,IAAI,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC;gBAC7B,KAAK,GAAG,CAAC,KAAK,CAAC;gBACf,IAAI,IAAI,KAAK,GAAG,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC;gBAC1B,IAAI,IAAI,KAAK,GAAG,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YAClC,CAAC;YAED,uCAAuC;YACvC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,GAAG,MAAM,CAAC;YAC9B,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;YACnB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,IAAI,EAAE,EAAE,CAAC,EAAE;gBAC1B,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,MAAM,GAAG,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC;YACzC,MAAM,KAAK,GAAG,KAAK,GAAG,IAAI,CAAC;YAC3B,MAAM,IAAI,GAAG,EAAE,GAAG,KAAK,CAAC;YACxB,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;YACtB,IAAI,EAAE,GAAG,EAAE;gBACT,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,GAAG,KAAK,GAAG,IAAI,CAAC;YACzC,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;QAC1B,CAAC;QACD,OAAO;IACT,CAAC;IAED,iBAAiB;IACjB,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;IACX,IAAI,MAAM,GAAG,EAAE,CAAC;IAEhB,KAAK,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,IAAI,CAAC,EAAE,EAAE,EAAE,EAAE,CAAC;QAC/B,MAAM,GAAG,GAAG,EAAE,CAAC;QACf,MAAM,IAAI,GAAG,EAAE,GAAG,CAAC,CAAC;QAEpB,mCAAmC;QACnC,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC;QACd,KAAK,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE;YAC9B,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,GAAG,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;QAClC,EAAE,CAAC,CAAC,CAAC,IAAI,GAAG,CAAC;QAEb,uCAAuC;QACvC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,IAAI,IAAI,EAAE,CAAC,EAAE;YAC5B,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;QAChC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC;QACnB,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC;QACxB,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QACtC,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,EAAE,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC1C,MAAM,IAAI,GAAG,CAAC;IAChB,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import {LsodaContext} from './common';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Set coefficients for the current method.
|
|
5
|
+
* Computes elco and tesco arrays for all orders.
|
|
6
|
+
* meth=1: Adams (orders 1-12), meth=2: BDF (orders 1-5).
|
|
7
|
+
*/
|
|
8
|
+
export function cfode(ctx: LsodaContext, meth: number): void {
|
|
9
|
+
const c = ctx.common!;
|
|
10
|
+
const pc = new Float64Array(13);
|
|
11
|
+
|
|
12
|
+
if (meth === 1) {
|
|
13
|
+
c.elco[1][1] = 1.;
|
|
14
|
+
c.elco[1][2] = 1.;
|
|
15
|
+
c.tesco[1][1] = 0.;
|
|
16
|
+
c.tesco[1][2] = 2.;
|
|
17
|
+
c.tesco[2][1] = 1.;
|
|
18
|
+
c.tesco[12][3] = 0.;
|
|
19
|
+
pc[1] = 1.;
|
|
20
|
+
let rqfac = 1.;
|
|
21
|
+
|
|
22
|
+
for (let nq = 2; nq <= 12; nq++) {
|
|
23
|
+
const rq1fac = rqfac;
|
|
24
|
+
rqfac = rqfac / nq;
|
|
25
|
+
const nqm1 = nq - 1;
|
|
26
|
+
const fnqm1 = nqm1;
|
|
27
|
+
const nqp1 = nq + 1;
|
|
28
|
+
|
|
29
|
+
// Form coefficients of p(x)*(x+nq-1)
|
|
30
|
+
pc[nq] = 0.;
|
|
31
|
+
for (let i = nq; i >= 2; i--)
|
|
32
|
+
pc[i] = pc[i - 1] + fnqm1 * pc[i];
|
|
33
|
+
pc[1] = fnqm1 * pc[1];
|
|
34
|
+
|
|
35
|
+
// Compute integral, -1 to 0, of p(x) and x*p(x)
|
|
36
|
+
let pint = pc[1];
|
|
37
|
+
let xpin = pc[1] / 2.;
|
|
38
|
+
let tsign = 1.;
|
|
39
|
+
for (let i = 2; i <= nq; i++) {
|
|
40
|
+
tsign = -tsign;
|
|
41
|
+
pint += tsign * pc[i] / i;
|
|
42
|
+
xpin += tsign * pc[i] / (i + 1);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
// Store coefficients in elco and tesco
|
|
46
|
+
c.elco[nq][1] = pint * rq1fac;
|
|
47
|
+
c.elco[nq][2] = 1.;
|
|
48
|
+
for (let i = 2; i <= nq; i++)
|
|
49
|
+
c.elco[nq][i + 1] = rq1fac * pc[i] / i;
|
|
50
|
+
const agamq = rqfac * xpin;
|
|
51
|
+
const ragq = 1. / agamq;
|
|
52
|
+
c.tesco[nq][2] = ragq;
|
|
53
|
+
if (nq < 12)
|
|
54
|
+
c.tesco[nqp1][1] = ragq * rqfac / nqp1;
|
|
55
|
+
c.tesco[nqm1][3] = ragq;
|
|
56
|
+
}
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
// meth = 2 (BDF)
|
|
61
|
+
pc[1] = 1.;
|
|
62
|
+
let rq1fac = 1.;
|
|
63
|
+
|
|
64
|
+
for (let nq = 1; nq <= 5; nq++) {
|
|
65
|
+
const fnq = nq;
|
|
66
|
+
const nqp1 = nq + 1;
|
|
67
|
+
|
|
68
|
+
// Form coefficients of p(x)*(x+nq)
|
|
69
|
+
pc[nqp1] = 0.;
|
|
70
|
+
for (let i = nq + 1; i >= 2; i--)
|
|
71
|
+
pc[i] = pc[i - 1] + fnq * pc[i];
|
|
72
|
+
pc[1] *= fnq;
|
|
73
|
+
|
|
74
|
+
// Store coefficients in elco and tesco
|
|
75
|
+
for (let i = 1; i <= nqp1; i++)
|
|
76
|
+
c.elco[nq][i] = pc[i] / pc[2];
|
|
77
|
+
c.elco[nq][2] = 1.;
|
|
78
|
+
c.tesco[nq][1] = rq1fac;
|
|
79
|
+
c.tesco[nq][2] = nqp1 / c.elco[nq][1];
|
|
80
|
+
c.tesco[nq][3] = (nq + 2) / c.elco[nq][1];
|
|
81
|
+
rq1fac /= fnq;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
// Constants from common.h
|
|
2
|
+
export const ETA = 2.2204460492503131e-16;
|
|
3
|
+
export const SQRTETA = 1.4901161193847656e-08;
|
|
4
|
+
export const CCMAX = 0.3;
|
|
5
|
+
export const MAXCOR = 3;
|
|
6
|
+
export const MSBP = 20;
|
|
7
|
+
export const MXNCF = 10;
|
|
8
|
+
export const RATIO = 5.0;
|
|
9
|
+
// Stability region limits for Adams method (from common.c)
|
|
10
|
+
export const sm1 = [
|
|
11
|
+
0., 0.5, 0.575, 0.55, 0.45, 0.35, 0.25, 0.2, 0.15, 0.1, 0.075, 0.05, 0.025,
|
|
12
|
+
];
|
|
13
|
+
// Method switch coefficients (from methodswitch.c)
|
|
14
|
+
// cm1 and cm2 are calculated from tesco/elco 1 and 2 formula in cfode.c
|
|
15
|
+
export const cm1 = [
|
|
16
|
+
0, 2.0, 5.999999999999998, 4.0,
|
|
17
|
+
1.5780346820809881, 0.44444444444444464, 0.09712509625876042, 0.017636684303350972,
|
|
18
|
+
0.002666977809498494, 0.00033760591160674403, 0.000035714285714285924, 3.1001984126984256e-06,
|
|
19
|
+
2.1543369643350994e-07,
|
|
20
|
+
];
|
|
21
|
+
export const cm2 = [
|
|
22
|
+
0, 2.0, 1.5, 0.6666666666666667,
|
|
23
|
+
0.20833333333333348, 0.04999999999999998, 0.09712509625876042, 0.017636684303350972,
|
|
24
|
+
0.002666977809498494, 0.00033760591160674403, 0.000035714285714285924, 3.1001984126984256e-06,
|
|
25
|
+
2.1543369643350994e-07,
|
|
26
|
+
];
|
|
27
|
+
// Internal solver state (mirrors lsoda_common_t)
|
|
28
|
+
export class LsodaCommon {
|
|
29
|
+
constructor() {
|
|
30
|
+
// Solution history (2D: yh[j][i], 1-indexed)
|
|
31
|
+
this.yh = [];
|
|
32
|
+
// Working matrix for Jacobian/LU (2D: wm[i][j], 1-indexed)
|
|
33
|
+
this.wm = [];
|
|
34
|
+
// Error weights (1-indexed)
|
|
35
|
+
this.ewt = new Float64Array(0);
|
|
36
|
+
// Saved function values (1-indexed)
|
|
37
|
+
this.savf = new Float64Array(0);
|
|
38
|
+
// Accumulated corrections (1-indexed)
|
|
39
|
+
this.acor = new Float64Array(0);
|
|
40
|
+
// Pivot indices for LU (1-indexed)
|
|
41
|
+
this.ipvt = new Int32Array(0);
|
|
42
|
+
// Step size
|
|
43
|
+
this.h = 0;
|
|
44
|
+
this.hu = 0;
|
|
45
|
+
this.rc = 0;
|
|
46
|
+
this.tn = 0;
|
|
47
|
+
this.tsw = 0;
|
|
48
|
+
this.pdnorm = 0;
|
|
49
|
+
// Convergence
|
|
50
|
+
this.crate = 0;
|
|
51
|
+
this.el = new Float64Array(14);
|
|
52
|
+
this.hold = 0;
|
|
53
|
+
this.rmax = 0;
|
|
54
|
+
this.pdest = 0;
|
|
55
|
+
this.pdlast = 0;
|
|
56
|
+
// Method coefficients (2D arrays, 1-indexed)
|
|
57
|
+
this.elco = [];
|
|
58
|
+
this.tesco = [];
|
|
59
|
+
// Counters and flags
|
|
60
|
+
this.ialth = 0;
|
|
61
|
+
this.ipup = 0;
|
|
62
|
+
this.nslp = 0;
|
|
63
|
+
this.icount = 0;
|
|
64
|
+
this.irflag = 0;
|
|
65
|
+
this.imxer = 0;
|
|
66
|
+
this.illin = 0;
|
|
67
|
+
this.nhnil = 0;
|
|
68
|
+
this.nslast = 0;
|
|
69
|
+
this.jcur = 0;
|
|
70
|
+
this.meth = 0;
|
|
71
|
+
this.mused = 0;
|
|
72
|
+
this.nq = 0;
|
|
73
|
+
this.nst = 0;
|
|
74
|
+
this.ncf = 0;
|
|
75
|
+
this.nfe = 0;
|
|
76
|
+
this.nje = 0;
|
|
77
|
+
this.nqu = 0;
|
|
78
|
+
this.miter = 0;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
// Solver context
|
|
82
|
+
export class LsodaContext {
|
|
83
|
+
constructor(func, neq, data) {
|
|
84
|
+
this.error = null;
|
|
85
|
+
this.common = null;
|
|
86
|
+
this.opt = null;
|
|
87
|
+
this.snapshots = null;
|
|
88
|
+
this.func = func;
|
|
89
|
+
this.neq = neq;
|
|
90
|
+
this.data = data !== null && data !== void 0 ? data : null;
|
|
91
|
+
this.state = 1;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
//# sourceMappingURL=common.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.js","sourceRoot":"","sources":["common.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
// Constants from common.h
|
|
2
|
+
export const ETA = 2.2204460492503131e-16;
|
|
3
|
+
export const SQRTETA = 1.4901161193847656e-08;
|
|
4
|
+
export const CCMAX = 0.3;
|
|
5
|
+
export const MAXCOR = 3;
|
|
6
|
+
export const MSBP = 20;
|
|
7
|
+
export const MXNCF = 10;
|
|
8
|
+
export const RATIO = 5.0;
|
|
9
|
+
|
|
10
|
+
// Stability region limits for Adams method (from common.c)
|
|
11
|
+
export const sm1: number[] = [
|
|
12
|
+
0., 0.5, 0.575, 0.55, 0.45, 0.35, 0.25, 0.2, 0.15, 0.1, 0.075, 0.05, 0.025,
|
|
13
|
+
];
|
|
14
|
+
|
|
15
|
+
// Method switch coefficients (from methodswitch.c)
|
|
16
|
+
// cm1 and cm2 are calculated from tesco/elco 1 and 2 formula in cfode.c
|
|
17
|
+
export const cm1: number[] = [
|
|
18
|
+
0, 2.0, 5.999999999999998, 4.0,
|
|
19
|
+
1.5780346820809881, 0.44444444444444464, 0.09712509625876042, 0.017636684303350972,
|
|
20
|
+
0.002666977809498494, 0.00033760591160674403, 0.000035714285714285924, 3.1001984126984256e-06,
|
|
21
|
+
2.1543369643350994e-07,
|
|
22
|
+
];
|
|
23
|
+
|
|
24
|
+
export const cm2: number[] = [
|
|
25
|
+
0, 2.0, 1.5, 0.6666666666666667,
|
|
26
|
+
0.20833333333333348, 0.04999999999999998, 0.09712509625876042, 0.017636684303350972,
|
|
27
|
+
0.002666977809498494, 0.00033760591160674403, 0.000035714285714285924, 3.1001984126984256e-06,
|
|
28
|
+
2.1543369643350994e-07,
|
|
29
|
+
];
|
|
30
|
+
|
|
31
|
+
// User-provided ODE function type
|
|
32
|
+
// t: current time, y: state vector (0-based), ydot: output derivatives (0-based), data: user data
|
|
33
|
+
export type LsodaFunc = (t: number, y: Float64Array, ydot: Float64Array, data: any) => number;
|
|
34
|
+
|
|
35
|
+
// Solver options
|
|
36
|
+
export interface LsodaOpt {
|
|
37
|
+
ixpr: number; // print flag
|
|
38
|
+
mxstep: number; // max internal steps per call
|
|
39
|
+
mxhnil: number; // max step size warnings
|
|
40
|
+
mxordn: number; // max Adams order (1-12)
|
|
41
|
+
mxords: number; // max BDF order (1-5)
|
|
42
|
+
tcrit: number; // critical time for itask 4,5
|
|
43
|
+
h0: number; // initial step size (0 = auto)
|
|
44
|
+
hmax: number; // max absolute step size
|
|
45
|
+
hmin: number; // min absolute step size
|
|
46
|
+
hmxi: number; // 1/hmax (computed)
|
|
47
|
+
itask: number; // integration task (1-5)
|
|
48
|
+
rtol: Float64Array; // relative tolerance (1-indexed)
|
|
49
|
+
atol: Float64Array; // absolute tolerance (1-indexed)
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
// Internal solver state (mirrors lsoda_common_t)
|
|
53
|
+
export class LsodaCommon {
|
|
54
|
+
// Solution history (2D: yh[j][i], 1-indexed)
|
|
55
|
+
yh: Float64Array[] = [];
|
|
56
|
+
// Working matrix for Jacobian/LU (2D: wm[i][j], 1-indexed)
|
|
57
|
+
wm: Float64Array[] = [];
|
|
58
|
+
// Error weights (1-indexed)
|
|
59
|
+
ewt: Float64Array = new Float64Array(0);
|
|
60
|
+
// Saved function values (1-indexed)
|
|
61
|
+
savf: Float64Array = new Float64Array(0);
|
|
62
|
+
// Accumulated corrections (1-indexed)
|
|
63
|
+
acor: Float64Array = new Float64Array(0);
|
|
64
|
+
// Pivot indices for LU (1-indexed)
|
|
65
|
+
ipvt: Int32Array = new Int32Array(0);
|
|
66
|
+
|
|
67
|
+
// Step size
|
|
68
|
+
h: number = 0;
|
|
69
|
+
hu: number = 0;
|
|
70
|
+
rc: number = 0;
|
|
71
|
+
tn: number = 0;
|
|
72
|
+
tsw: number = 0;
|
|
73
|
+
pdnorm: number = 0;
|
|
74
|
+
|
|
75
|
+
// Convergence
|
|
76
|
+
crate: number = 0;
|
|
77
|
+
el: Float64Array = new Float64Array(14);
|
|
78
|
+
hold: number = 0;
|
|
79
|
+
rmax: number = 0;
|
|
80
|
+
pdest: number = 0;
|
|
81
|
+
pdlast: number = 0;
|
|
82
|
+
|
|
83
|
+
// Method coefficients (2D arrays, 1-indexed)
|
|
84
|
+
elco: Float64Array[] = [];
|
|
85
|
+
tesco: Float64Array[] = [];
|
|
86
|
+
|
|
87
|
+
// Counters and flags
|
|
88
|
+
ialth: number = 0;
|
|
89
|
+
ipup: number = 0;
|
|
90
|
+
nslp: number = 0;
|
|
91
|
+
icount: number = 0;
|
|
92
|
+
irflag: number = 0;
|
|
93
|
+
imxer: number = 0;
|
|
94
|
+
illin: number = 0;
|
|
95
|
+
nhnil: number = 0;
|
|
96
|
+
nslast: number = 0;
|
|
97
|
+
jcur: number = 0;
|
|
98
|
+
meth: number = 0;
|
|
99
|
+
mused: number = 0;
|
|
100
|
+
nq: number = 0;
|
|
101
|
+
nst: number = 0;
|
|
102
|
+
ncf: number = 0;
|
|
103
|
+
nfe: number = 0;
|
|
104
|
+
nje: number = 0;
|
|
105
|
+
nqu: number = 0;
|
|
106
|
+
miter: number = 0;
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
// Snapshot of the Nordsieck array at a successful step (0-based arrays)
|
|
110
|
+
export interface NordsieckSnapshot {
|
|
111
|
+
tn: number; // right edge of the step
|
|
112
|
+
h: number; // step size used
|
|
113
|
+
hu: number; // last successful step size (for range check)
|
|
114
|
+
nq: number; // method order
|
|
115
|
+
yh: Float64Array[]; // yh[0..nq], each of length neq (0-based copies)
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
// Solver context
|
|
119
|
+
export class LsodaContext {
|
|
120
|
+
func: LsodaFunc;
|
|
121
|
+
data: any;
|
|
122
|
+
neq: number;
|
|
123
|
+
state: number;
|
|
124
|
+
error: string | null = null;
|
|
125
|
+
common: LsodaCommon | null = null;
|
|
126
|
+
opt: LsodaOpt | null = null;
|
|
127
|
+
snapshots: NordsieckSnapshot[] | null = null;
|
|
128
|
+
|
|
129
|
+
constructor(func: LsodaFunc, neq: number, data?: any) {
|
|
130
|
+
this.func = func;
|
|
131
|
+
this.neq = neq;
|
|
132
|
+
this.data = data ?? null;
|
|
133
|
+
this.state = 1;
|
|
134
|
+
}
|
|
135
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { MXNCF } from './common';
|
|
2
|
+
/**
|
|
3
|
+
* Handle corrector convergence failure.
|
|
4
|
+
* Retracts yh array and increments ncf.
|
|
5
|
+
* Returns 2 if unrecoverable, 1 if step can be retried.
|
|
6
|
+
*/
|
|
7
|
+
export function corfailure(ctx, told) {
|
|
8
|
+
const c = ctx.common;
|
|
9
|
+
const neq = ctx.neq;
|
|
10
|
+
const hmin = ctx.opt.hmin;
|
|
11
|
+
c.ncf++;
|
|
12
|
+
c.rmax = 2.;
|
|
13
|
+
c.tn = told;
|
|
14
|
+
for (let j = c.nq; j >= 1; j--) {
|
|
15
|
+
for (let i1 = j; i1 <= c.nq; i1++) {
|
|
16
|
+
for (let i = 1; i <= neq; i++)
|
|
17
|
+
c.yh[i1][i] -= c.yh[i1 + 1][i];
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
if (Math.abs(c.h) <= hmin * 1.00001 || c.ncf === MXNCF)
|
|
21
|
+
return 2;
|
|
22
|
+
c.ipup = c.miter;
|
|
23
|
+
return 1;
|
|
24
|
+
}
|
|
25
|
+
//# sourceMappingURL=corfailure.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"corfailure.js","sourceRoot":"","sources":["corfailure.ts"],"names":[],"mappings":"AAAA,OAAO,EAAe,KAAK,EAAC,MAAM,UAAU,CAAC;AAE7C;;;;GAIG;AACH,MAAM,UAAU,UAAU,CAAC,GAAiB,EAAE,IAAY;IACxD,MAAM,CAAC,GAAG,GAAG,CAAC,MAAO,CAAC;IACtB,MAAM,GAAG,GAAG,GAAG,CAAC,GAAG,CAAC;IACpB,MAAM,IAAI,GAAG,GAAG,CAAC,GAAI,CAAC,IAAI,CAAC;IAE3B,CAAC,CAAC,GAAG,EAAE,CAAC;IACR,CAAC,CAAC,IAAI,GAAG,EAAE,CAAC;IACZ,CAAC,CAAC,EAAE,GAAG,IAAI,CAAC;IAEZ,KAAK,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC;QAC/B,KAAK,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,IAAI,CAAC,CAAC,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC;YAClC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,IAAI,GAAG,EAAE,CAAC,EAAE;gBAC3B,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACnC,CAAC;IACH,CAAC;IAED,IAAI,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,IAAI,GAAG,OAAO,IAAI,CAAC,CAAC,GAAG,KAAK,KAAK;QACpD,OAAO,CAAC,CAAC;IAGX,CAAC,CAAC,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC;IACjB,OAAO,CAAC,CAAC;AACX,CAAC"}
|