This commit is contained in:
parent
8e3d4490bd
commit
e4bf065222
|
@ -2,6 +2,7 @@ package com.rusefi;
|
|||
|
||||
import com.rusefi.ui.MessagesView;
|
||||
import com.rusefi.ui.util.UiUtils;
|
||||
import com.rusefi.ui.widgets.EtbMonteCarloSequence;
|
||||
import com.rusefi.ui.widgets.EtbResearch;
|
||||
import com.rusefi.ui.widgets.EtbTestSequence;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
@ -25,6 +26,7 @@ public class BenchTestPane {
|
|||
content.add(createIdleTest());
|
||||
content.add(createDizzyTest());
|
||||
content.add(UiUtils.wrap(new EtbTestSequence().getButton()));
|
||||
content.add(UiUtils.wrap(new EtbMonteCarloSequence().getButton()));
|
||||
content.add(UiUtils.wrap(new EtbResearch().getButton()));
|
||||
content.add(new MessagesView().messagesScroll);
|
||||
}
|
||||
|
|
|
@ -14,6 +14,8 @@ import java.util.concurrent.TimeUnit;
|
|||
/**
|
||||
* https://github.com/rusefi/rusefi/issues/494
|
||||
* <p>
|
||||
* https://en.wikipedia.org/wiki/Standard_deviation of error posted to specified sensor
|
||||
* <p>
|
||||
* 11/16/2017
|
||||
* (c) Andrey Belomutskiy
|
||||
*
|
||||
|
@ -25,6 +27,7 @@ public class ClosedLoopControlQualityMetric {
|
|||
private final ValueSource target;
|
||||
private final ValueSource result;
|
||||
private final Sensor destination;
|
||||
private boolean isStarted;
|
||||
|
||||
/**
|
||||
* Buffer of recent error measurements
|
||||
|
@ -43,6 +46,10 @@ public class ClosedLoopControlQualityMetric {
|
|||
}
|
||||
|
||||
public void start(int bufferSize, int periodMs) {
|
||||
if (isStarted)
|
||||
return;
|
||||
isStarted = true;
|
||||
|
||||
errorsBuffer = new CyclicBuffer(bufferSize);
|
||||
executor.scheduleAtFixedRate(() -> {
|
||||
rememberCurrentError(target.getValue() - result.getValue());
|
||||
|
|
|
@ -0,0 +1,73 @@
|
|||
package com.rusefi.ui.widgets;
|
||||
|
||||
import com.rusefi.core.MessagesCentral;
|
||||
import com.rusefi.core.Sensor;
|
||||
import com.rusefi.core.SensorCentral;
|
||||
import com.rusefi.io.CommandQueue;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
import static com.rusefi.Timeouts.SECOND;
|
||||
import static com.rusefi.ui.widgets.EtbTestSequence.*;
|
||||
|
||||
/**
|
||||
* 3/2/2019
|
||||
* (c) Andrey Belomutskiy
|
||||
*/
|
||||
public class EtbMonteCarloSequence {
|
||||
public static final int LIMIT = 100;
|
||||
private final JButton button = new JButton("ETB I feel lucky!");
|
||||
private final static Random r = new Random();
|
||||
private int counter;
|
||||
|
||||
public EtbMonteCarloSequence() {
|
||||
button.addActionListener(e -> {
|
||||
counter = 0;
|
||||
|
||||
// 3000 data points at 10Hz should be 300 seconds worth of data
|
||||
metric.start(/* buffer size: */3000, /*period, ms: */ 100);
|
||||
|
||||
executor.execute(this::runRandomCycle);
|
||||
});
|
||||
}
|
||||
|
||||
private void runRandomCycle() {
|
||||
final int offset = r.nextInt(100);
|
||||
final double pFactor = 1 + (r.nextInt(300) / 100.0);
|
||||
final double iFactor = r.nextInt(30) / 100.0;
|
||||
final double dFactor = r.nextInt(30) / 100.0;
|
||||
String stats = "mcstats:offset:" + offset +
|
||||
":pFactor:" + pFactor +
|
||||
":iFactor:" + iFactor +
|
||||
":dFactor:" + dFactor;
|
||||
MessagesCentral.getInstance().postMessage(EtbMonteCarloSequence.class, stats);
|
||||
CommandQueue.getInstance().write("set etb_o " + offset);
|
||||
CommandQueue.getInstance().write("set etb_p " + pFactor);
|
||||
CommandQueue.getInstance().write("set etb_i " + iFactor);
|
||||
CommandQueue.getInstance().write("set etb_d " + dFactor);
|
||||
|
||||
SequenceStep firstStep = new EtbTarget(10 * SECOND, 4 /*position*/);
|
||||
SequenceStep last = addSequence(firstStep);
|
||||
last.addNext(new SequenceStep(5 * SECOND) {
|
||||
@Override
|
||||
protected void doJob() {
|
||||
double result = SensorCentral.getInstance().getValue(Sensor.ETB_CONTROL_QUALITY);
|
||||
MessagesCentral.getInstance().postMessage(EtbMonteCarloSequence.class, stats + ":result:" + result);
|
||||
if (counter == LIMIT) {
|
||||
MessagesCentral.getInstance().postMessage(EtbTestSequence.class, "ETB MC sequence done!");
|
||||
return;
|
||||
}
|
||||
counter++;
|
||||
MessagesCentral.getInstance().postMessage(EtbTestSequence.class, "Starting " + counter + " of " + LIMIT);
|
||||
runRandomCycle();
|
||||
}
|
||||
});
|
||||
firstStep.execute(executor);
|
||||
}
|
||||
|
||||
public JButton getButton() {
|
||||
return button;
|
||||
}
|
||||
}
|
|
@ -6,6 +6,7 @@ import com.rusefi.core.MessagesCentral;
|
|||
import com.rusefi.core.Sensor;
|
||||
import com.rusefi.core.SensorCentral;
|
||||
import com.rusefi.io.CommandQueue;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.util.concurrent.Executors;
|
||||
|
@ -26,14 +27,18 @@ import java.util.concurrent.TimeUnit;
|
|||
* @see TimeBasedBuffer
|
||||
*/
|
||||
public class EtbTestSequence {
|
||||
private final ScheduledExecutorService executor = Executors.newSingleThreadScheduledExecutor();
|
||||
private boolean isStarted;
|
||||
protected static final ScheduledExecutorService executor = Executors.newSingleThreadScheduledExecutor();
|
||||
|
||||
protected final ClosedLoopControlQualityMetric metric = new ClosedLoopControlQualityMetric(
|
||||
SensorCentral.getInstance().getValueSource(Sensor.PPS),
|
||||
SensorCentral.getInstance().getValueSource(Sensor.TPS),
|
||||
Sensor.ETB_CONTROL_QUALITY
|
||||
);
|
||||
protected final static ClosedLoopControlQualityMetric metric = createMetric();
|
||||
|
||||
@NotNull
|
||||
protected static ClosedLoopControlQualityMetric createMetric() {
|
||||
return new ClosedLoopControlQualityMetric(
|
||||
SensorCentral.getInstance().getValueSource(Sensor.PPS),
|
||||
SensorCentral.getInstance().getValueSource(Sensor.TPS),
|
||||
Sensor.ETB_CONTROL_QUALITY
|
||||
);
|
||||
}
|
||||
|
||||
private final static long SECOND = 1000;
|
||||
|
||||
|
@ -42,7 +47,11 @@ public class EtbTestSequence {
|
|||
private SequenceStep FIRST_STEP = new EtbTarget(10 * SECOND, 4 /*position*/);
|
||||
|
||||
{
|
||||
FIRST_STEP.add(new SequenceStep(SECOND) {
|
||||
addSequence(FIRST_STEP);
|
||||
}
|
||||
|
||||
protected static SequenceStep addSequence(SequenceStep first_step) {
|
||||
return first_step.addNext(new SequenceStep(SECOND) {
|
||||
@Override
|
||||
protected void doJob() {
|
||||
metric.reset();
|
||||
|
@ -56,24 +65,38 @@ public class EtbTestSequence {
|
|||
.addNext(5 * SECOND, 2 /*position*/)
|
||||
.addNext(5 * SECOND, 0 /*position*/)
|
||||
.addNext(5 * SECOND, 10 /*position*/)
|
||||
.addNext(10 * SECOND, 6 /*position*/)
|
||||
.addNext(10 * SECOND, 30 /*position*/)
|
||||
.addNext(10 * SECOND, 50 /*position*/)
|
||||
.addNext(10 * SECOND, 70 /*position*/)
|
||||
.addNext(10 * SECOND, 100 /*position*/)
|
||||
.addNext(10 * SECOND, 50 /*position*/)
|
||||
.addNext(10 * SECOND, 70 /*position*/)
|
||||
.addNext(10 * SECOND, 4 /*position*/)
|
||||
.addNext(10 * SECOND, 0 /*position*/)
|
||||
;
|
||||
.addNext(3 * SECOND, 0 /*position*/)
|
||||
.addNext(1 * SECOND, 6 /*position*/)
|
||||
.addNext(1 * SECOND, 8 /*position*/)
|
||||
.addNext(1 * SECOND, 6 /*position*/)
|
||||
.addNext(1 * SECOND, 4 /*position*/)
|
||||
.addNext(1 * SECOND, 2 /*position*/)
|
||||
.addNext(1 * SECOND, 0 /*position*/)
|
||||
.addNext(1 * SECOND, 10 /*position*/)
|
||||
.addNext(3 * SECOND, 7 /*position*/)
|
||||
.addNext(3 * SECOND, 6 /*position*/)
|
||||
.addNext(3 * SECOND, 5 /*position*/)
|
||||
.addNext(3 * SECOND, 4 /*position*/)
|
||||
.addNext(3 * SECOND, 3 /*position*/)
|
||||
.addNext(3 * SECOND, 2 /*position*/)
|
||||
.addNext(3 * SECOND, 1 /*position*/)
|
||||
.addNext(3 * SECOND, 0 /*position*/)
|
||||
// .addNext(10 * SECOND, 6 /*position*/)
|
||||
// .addNext(10 * SECOND, 30 /*position*/)
|
||||
// .addNext(10 * SECOND, 50 /*position*/)
|
||||
// .addNext(10 * SECOND, 70 /*position*/)
|
||||
// .addNext(10 * SECOND, 100 /*position*/)
|
||||
// .addNext(10 * SECOND, 50 /*position*/)
|
||||
// .addNext(10 * SECOND, 70 /*position*/)
|
||||
// .addNext(10 * SECOND, 4 /*position*/)
|
||||
// .addNext(10 * SECOND, 0 /*position*/)
|
||||
;
|
||||
}
|
||||
|
||||
public EtbTestSequence() {
|
||||
button.addActionListener(e -> {
|
||||
if (!isStarted) {
|
||||
metric.start(/* buffer size: */1000, /*period, ms: */ 100);
|
||||
isStarted = true;
|
||||
}
|
||||
// 3000 data points at 10Hz should be 300 seconds worth of data
|
||||
metric.start(/* buffer size: */3000, /*period, ms: */ 100);
|
||||
FIRST_STEP.execute(executor);
|
||||
});
|
||||
}
|
||||
|
@ -93,7 +116,7 @@ public class EtbTestSequence {
|
|||
public void execute(ScheduledExecutorService executor) {
|
||||
doJob();
|
||||
if (next != null) {
|
||||
FileLog.MAIN.logLine("Scheduling " + next);
|
||||
FileLog.MAIN.logLine("Scheduling " + next + " with " + duration + "ms delay");
|
||||
executor.schedule(() -> next.execute(executor), duration, TimeUnit.MILLISECONDS);
|
||||
} else {
|
||||
MessagesCentral.getInstance().postMessage(EtbTestSequence.class, "ETB test sequence done!");
|
||||
|
@ -103,10 +126,10 @@ public class EtbTestSequence {
|
|||
protected abstract void doJob();
|
||||
|
||||
public SequenceStep addNext(long duration, double position) {
|
||||
return add(new EtbTarget(duration, position));
|
||||
return addNext(new EtbTarget(duration, position));
|
||||
}
|
||||
|
||||
private SequenceStep add(SequenceStep step) {
|
||||
public SequenceStep addNext(SequenceStep step) {
|
||||
next = step;
|
||||
return next;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue