ETB monte carlo keeps track of best result

This commit is contained in:
rusefi 2019-05-04 09:57:57 -04:00
parent 91467220b2
commit ea5ac54bee
6 changed files with 121 additions and 57 deletions

View File

@ -241,6 +241,36 @@ void setFrankensoBoardTestConfiguration(DECLARE_CONFIG_PARAMETER_SIGNATURE) {
}
void setBoschVNH2SP30Curve(DECLARE_ENGINE_PARAMETER_SIGNATURE) {
engineConfiguration->etbBiasBins[0] = 0;
engineConfiguration->etbBiasBins[1] = 1;
engineConfiguration->etbBiasBins[2] = 2;
/**
* This specific throttle has default position of about 7% open
*/
engineConfiguration->etbBiasBins[3] = 4;
engineConfiguration->etbBiasBins[4] = 7;
engineConfiguration->etbBiasBins[5] = 98;
engineConfiguration->etbBiasBins[6] = 99;
engineConfiguration->etbBiasBins[7] = 100;
/**
* Some negative bias for below-default position
*/
engineConfiguration->etbBiasValues[0] = -20;
engineConfiguration->etbBiasValues[1] = -18;
engineConfiguration->etbBiasValues[2] = -17;
/**
* Zero bias for index which corresponds to default throttle position, when no current is applied
* This specific throttle has default position of about 7% open
*/
engineConfiguration->etbBiasValues[3] = 0;
engineConfiguration->etbBiasValues[4] = 20;
engineConfiguration->etbBiasValues[5] = 21;
engineConfiguration->etbBiasValues[6] = 22;
engineConfiguration->etbBiasValues[7] = 25;
}
// ETB_BENCH_ENGINE
// set engine_type 58
void setEtbTestConfiguration(DECLARE_CONFIG_PARAMETER_SIGNATURE) {
@ -266,7 +296,8 @@ void setEtbTestConfiguration(DECLARE_CONFIG_PARAMETER_SIGNATURE) {
CONFIGB(etb1.controlPin1) = GPIOE_14;
#if EFI_ELECTRONIC_THROTTLE_BODY
setDefaultEtbParameters(PASS_CONFIG_PARAMETER_SIGNATURE);
setBoschVNH2SP30Curve(PASS_CONFIG_PARAMETER_SIGNATURE);
// setDefaultEtbParameters(PASS_CONFIG_PARAMETER_SIGNATURE);
// values are above 100% since we have feedforward part of the total summation
engineConfiguration->etb.minValue = -200;
engineConfiguration->etb.maxValue = 200;

View File

@ -9,8 +9,8 @@ public class EtbTarget extends TestSequenceStep {
private final double position;
private final Runnable onEachStep;
public EtbTarget(long duration, double position, Runnable onEachStep) {
super(duration);
public EtbTarget(long duration, double position, Runnable onEachStep, Condition condition) {
super(duration, condition);
this.position = position;
this.onEachStep = onEachStep;
}
@ -24,7 +24,7 @@ public class EtbTarget extends TestSequenceStep {
@Override
public String toString() {
return "EtbTarget{" +
"duration=" + duration +
"nextStepDelay=" + nextStepDelay +
", position=" + position +
'}';
}

View File

@ -18,47 +18,47 @@ public class StandardTestSequence {
);
}
public static TestSequenceStep addSequence(TestSequenceStep first_step, Runnable onEachStep) {
TestSequenceStep secondStep = new TestSequenceStep(SECOND) {
public static TestSequenceStep addSequence(TestSequenceStep first_step, Runnable onEachStep, TestSequenceStep.Condition condition) {
TestSequenceStep secondStep = new TestSequenceStep(SECOND, EtbTarget.Condition.YES) {
@Override
protected void doJob() {
metric.reset();
}
};
TestSequenceStep result = first_step.addNext(secondStep)
.addNext(10 * SECOND, 4 /*position*/, onEachStep)
.addNext(5 * SECOND, 6, /*position*/onEachStep)
.addNext(5 * SECOND, 8, /*position*/onEachStep)
.addNext(5 * SECOND, 6, /*position*/onEachStep)
.addNext(5 * SECOND, 4, /*position*/onEachStep)
.addNext(5 * SECOND, 2, /*position*/onEachStep)
.addNext(5 * SECOND, 0, /*position*/onEachStep)
.addNext(5 * SECOND, 10, /*position*/onEachStep)
.addNext(3 * SECOND, 0, /*position*/onEachStep)
.addNext(1 * SECOND, 6, /*position*/onEachStep)
.addNext(1 * SECOND, 8, /*position*/onEachStep)
.addNext(1 * SECOND, 6, /*position*/onEachStep)
.addNext(1 * SECOND, 4, /*position*/onEachStep)
.addNext(1 * SECOND, 2, /*position*/onEachStep)
.addNext(1 * SECOND, 0, /*position*/onEachStep)
.addNext(1 * SECOND, 10, /*position*/onEachStep)
.addNext(3 * SECOND, 7, /*position*/onEachStep)
.addNext(3 * SECOND, 6, /*position*/onEachStep)
.addNext(3 * SECOND, 5, /*position*/onEachStep)
.addNext(3 * SECOND, 4, /*position*/onEachStep)
.addNext(3 * SECOND, 3, /*position*/onEachStep)
.addNext(3 * SECOND, 2, /*position*/onEachStep)
.addNext(3 * SECOND, 1, /*position*/onEachStep)
.addNext(3 * SECOND, 0, /*position*/onEachStep)
.addNext(10 * SECOND, 6, /*position*/onEachStep)
.addNext(10 * SECOND, 30, /*position*/onEachStep)
.addNext(10 * SECOND, 50, /*position*/onEachStep)
.addNext(10 * SECOND, 70, /*position*/onEachStep)
.addNext(10 * SECOND, 95, /*position*/onEachStep)
.addNext(10 * SECOND, 50, /*position*/onEachStep)
.addNext(10 * SECOND, 70, /*position*/onEachStep)
.addNext(10 * SECOND, 4, /*position*/onEachStep)
.addNext(10 * SECOND, 0, /*position*/onEachStep)
.addNext(10 * SECOND, 4 /*position*/, onEachStep, condition)
.addNext(5 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 8, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 4, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 2, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 0, /*position*/onEachStep, condition)
.addNext(5 * SECOND, 10, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 0, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 8, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 4, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 2, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 0, /*position*/onEachStep, condition)
.addNext(1 * SECOND, 10, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 7, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 5, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 4, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 3, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 2, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 1, /*position*/onEachStep, condition)
.addNext(3 * SECOND, 0, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 6, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 30, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 50, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 70, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 95, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 50, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 70, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 4, /*position*/onEachStep, condition)
.addNext(10 * SECOND, 0, /*position*/onEachStep, condition)
;
return result;
}

View File

@ -7,18 +7,23 @@ import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
public abstract class TestSequenceStep {
protected final long duration;
/**
* First we execute {{@link #doJob()}} then we schedule next step for after 'nextStepDelay' time passes.
*/
protected final long nextStepDelay;
private final EtbTarget.Condition condition;
private TestSequenceStep next;
public TestSequenceStep(long duration) {
this.duration = duration;
public TestSequenceStep(long nextStepDelay, EtbTarget.Condition condition) {
this.nextStepDelay = nextStepDelay;
this.condition = condition;
}
public void execute(ScheduledExecutorService executor) {
doJob();
if (next != null) {
FileLog.MAIN.logLine("Scheduling " + next + " with " + duration + "ms delay");
executor.schedule(() -> next.execute(executor), duration, TimeUnit.MILLISECONDS);
if (next != null && condition.shouldContinue()) {
FileLog.MAIN.logLine("Scheduling " + next + " with " + nextStepDelay + "ms delay");
executor.schedule(() -> next.execute(executor), nextStepDelay, TimeUnit.MILLISECONDS);
} else {
MessagesCentral.getInstance().postMessage(TestSequenceStep.class, "ETB test sequence done!");
}
@ -26,8 +31,8 @@ public abstract class TestSequenceStep {
protected abstract void doJob();
public TestSequenceStep addNext(long duration, double position, Runnable onEachStep) {
return addNext(new EtbTarget(duration, position, onEachStep));
public TestSequenceStep addNext(long duration, double position, Runnable onEachStep, Condition condition) {
return addNext(new EtbTarget(duration, position, onEachStep, condition));
}
public TestSequenceStep addNext(TestSequenceStep step) {
@ -38,4 +43,10 @@ public abstract class TestSequenceStep {
public TestSequenceStep getNext() {
return next;
}
public interface Condition {
boolean shouldContinue();
Condition YES = () -> true;
}
}

View File

@ -22,10 +22,13 @@ import static com.rusefi.ui.etb.EtbTestSequence.*;
*/
public class EtbMonteCarloSequence {
public static final int LIMIT = 300;
private static final double DEFAULT_POSITION = 7;
private final JButton button = new JButton("ETB I feel lucky!");
private final static Random r = new Random();
private int counter;
private double bestResultSoFar = 75;
public EtbMonteCarloSequence() {
button.addActionListener(e -> {
counter = 0;
@ -33,6 +36,7 @@ public class EtbMonteCarloSequence {
// 3000 data points at 10Hz should be 300 seconds worth of data
StandardTestSequence.metric.start(/* buffer size: */3000, /*period, ms: */ 100);
// start first cycle. At the end of the run it would decide if it wants to start from beginning again
executor.execute(this::runRandomCycle);
});
}
@ -53,14 +57,32 @@ public class EtbMonteCarloSequence {
CommandQueue.getInstance().write("set etb_i " + iFactor);
CommandQueue.getInstance().write("set etb_d " + dFactor);
TestSequenceStep firstStep = new EtbTarget(10 * SECOND, 4, null);
TestSequenceStep last = StandardTestSequence.addSequence(firstStep, null);
last.addNext(new TestSequenceStep(5 * SECOND) {
TestSequenceStep firstStep = new EtbTarget(10 * SECOND, DEFAULT_POSITION, null, TestSequenceStep.Condition.YES);
TestSequenceStep.Condition condition = new TestSequenceStep.Condition() {
@Override
public boolean shouldContinue() {
double currentValue = StandardTestSequence.metric.getStandardDeviation();
boolean shouldContinue = currentValue < bestResultSoFar;
if (!shouldContinue) {
MessagesCentral.getInstance().postMessage(EtbMonteCarloSequence.class,
"Two much error accumulated, aborting! " + currentValue + " > " + bestResultSoFar);
}
return shouldContinue;
}
};
TestSequenceStep last = StandardTestSequence.addSequence(firstStep, null, condition);
last.addNext(new TestSequenceStep(5 * SECOND, EtbTarget.Condition.YES) {
@Override
protected void doJob() {
double result = SensorCentral.getInstance().getValue(Sensor.ETB_CONTROL_QUALITY);
double cycleResult = SensorCentral.getInstance().getValue(Sensor.ETB_CONTROL_QUALITY);
if (cycleResult < bestResultSoFar) {
bestResultSoFar = cycleResult;
MessagesCentral.getInstance().postMessage(EtbMonteCarloSequence.class,
getSecondsSinceFileStart() + ":" + stats + ":result:" + result);
getSecondsSinceFileStart() + ":" + stats + ":new_record:" + bestResultSoFar);
}
MessagesCentral.getInstance().postMessage(EtbMonteCarloSequence.class,
getSecondsSinceFileStart() + ":" + stats + ":result:" + cycleResult);
if (counter == LIMIT) {
MessagesCentral.getInstance().postMessage(EtbTestSequence.class, "ETB MC sequence done!");
return;

View File

@ -43,13 +43,13 @@ public class EtbTestSequence {
AtomicInteger stepCounter = new AtomicInteger();
AtomicInteger totalSteps = new AtomicInteger();
TestSequenceStep lastStep = new TestSequenceStep(SECOND) {
TestSequenceStep lastStep = new TestSequenceStep(SECOND, EtbTarget.Condition.YES) {
@Override
protected void doJob() {
button.setEnabled(true);
button.setText(BUTTON_TEXT);
double value = StandardTestSequence.metric.getStandardDeviation();
result.setText(String.format("Final Result: %.3f", value));
double finalValue = StandardTestSequence.metric.getStandardDeviation();
result.setText(String.format("Final Result: %.3f", finalValue));
}
};
@ -68,8 +68,8 @@ public class EtbTestSequence {
}
};
TestSequenceStep firstStep = new EtbTarget(10 * SECOND, 4, /*position*/onEachStep);
TestSequenceStep result = StandardTestSequence.addSequence(firstStep, onEachStep);
TestSequenceStep firstStep = new EtbTarget(10 * SECOND, 4, /*position*/onEachStep, TestSequenceStep.Condition.YES);
TestSequenceStep result = StandardTestSequence.addSequence(firstStep, onEachStep, TestSequenceStep.Condition.YES);
result.addNext(lastStep);
totalSteps.set(count(firstStep));