-
Notifications
You must be signed in to change notification settings - Fork 0
/
optimize.js
89 lines (81 loc) · 2.65 KB
/
optimize.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
// Optimize model using Monte Carlo method
"use strict";
// globals: document, window, CA
var SC = window.SC || {};
SC.monteCarloEnabled = false;
SC.monteCarloBest = 1e9;
SC.monteCarloRuns = 0;
SC.monteCarlo = function (aSpeedIS, aSpeedN, aSpeedRS) {
// Randomly change model and keep it if the difference is smaller
aSpeedIS = aSpeedIS || 0.1;
aSpeedN = aSpeedN || 0.1;
aSpeedRS = aSpeedRS || 0.1;
var d1 = SC.calculateDifference(SC.modelVA, SC.measuredVA).diff,
d2,
IS,
N,
RS,
nextVA,
vmax = SC.measuredVA[SC.measuredVA.length - 1][0],
temp = SC.fromEng(SC.e.temperature.value);
// slightly change model
IS = SC.model.IS * CA.randomFloat(1 - aSpeedIS, 1 + aSpeedIS);
N = SC.model.N * CA.randomFloat(1 - aSpeedN, 1 + aSpeedN);
RS = SC.model.RS * CA.randomFloat(1 - aSpeedRS, 1 + aSpeedRS);
// create new curve and measure difference against measured
nextVA = SC.diodeCurve(vmax, temp, IS, N, RS);
d2 = SC.calculateDifference(nextVA, SC.measuredVA).diff;
// if model is better keep it
if (d2 < d1) {
SC.model.IS = IS;
SC.model.N = N;
SC.model.RS = RS;
SC.modelVA = nextVA;
if (SC.chart1.series[1]) {
SC.chart1.series[1].data = SC.modelVA;
}
SC.chart1.render();
SC.showDifference();
SC.e.IS.value = IS.toPrecision(8);
SC.e.N.value = N.toPrecision(8);
SC.e.RS.value = RS.toPrecision(8);
SC.showSpiceModel();
return d2;
}
};
SC.monteCarloBatch = function (aSpeedIS, aSpeedN, aSpeedRS) {
// Run it 1000 times, repeat which optimize is running
var i, d;
for (i = 0; i < 1000; i++) {
SC.monteCarloRuns++;
// first 100k be more random
if (SC.monteCarloRuns < 99000) {
d = SC.monteCarlo(30 * aSpeedIS, 30 * aSpeedN, 30 * aSpeedRS);
} else {
d = SC.monteCarlo(aSpeedIS, aSpeedN, aSpeedRS);
}
if (d < SC.monteCarloBest) {
SC.monteCarloBest = d;
}
}
if (SC.monteCarloEnabled) {
window.requestAnimationFrame(function () {
SC.monteCarloBatch(aSpeedIS, aSpeedN, aSpeedRS);
});
}
};
SC.startMonteCarlo = function () {
// Start optimizing
SC.monteCarloRuns = 0;
SC.e.start_monte_carlo.disabled = true;
SC.e.stop_monte_carlo.disabled = false;
SC.monteCarloBest = 1e9;
SC.monteCarloEnabled = true;
SC.monteCarloBatch(0.001, 0.001, 0.001);
};
SC.stopMonteCarlo = function () {
// Stop optimizing
SC.e.start_monte_carlo.disabled = false;
SC.e.stop_monte_carlo.disabled = true;
SC.monteCarloEnabled = false;
};