Skip to content

Instantly share code, notes, and snippets.

@mtf90
Created April 18, 2020 12:43
Show Gist options
  • Save mtf90/ec6b73e8746f486a1b1809714479724b to your computer and use it in GitHub Desktop.
Save mtf90/ec6b73e8746f486a1b1809714479724b to your computer and use it in GitHub Desktop.
An example on how to construct a learning setup with a timeout. Uses LearnLib 0.15.0.
package com.github.mtf90;
import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
import de.learnlib.algorithms.ttt.dfa.TTTLearnerDFABuilder;
import de.learnlib.api.algorithm.LearningAlgorithm;
import de.learnlib.api.algorithm.LearningAlgorithm.DFALearner;
import de.learnlib.api.oracle.EquivalenceOracle;
import de.learnlib.api.oracle.EquivalenceOracle.DFAEquivalenceOracle;
import de.learnlib.api.oracle.MembershipOracle.DFAMembershipOracle;
import de.learnlib.api.query.DefaultQuery;
import de.learnlib.oracle.equivalence.DFASimulatorEQOracle;
import de.learnlib.oracle.membership.SimulatorOracle.DFASimulatorOracle;
import net.automatalib.automata.fsa.DFA;
import net.automatalib.automata.fsa.impl.compact.CompactDFA;
import net.automatalib.util.automata.random.RandomAutomata;
import net.automatalib.visualization.Visualization;
import net.automatalib.words.Alphabet;
import net.automatalib.words.impl.Alphabets;
/**
* An example on how to construct a learning setup with a timeout. Uses LearnLib 0.15.0.
*/
public final class TimeoutExample {
private TimeoutExample() {
// prevent instantiation
}
public static void main(String[] args) throws ExecutionException, InterruptedException {
final Alphabet<Character> inputs = Alphabets.characters('a', 'f');
final CompactDFA<Character> target = RandomAutomata.randomDFA(new Random(42), 100, inputs);
final DFAMembershipOracle<Character> mqOracle = new DFASimulatorOracle<>(target);
final DFALearner<Character> learner =
new TTTLearnerDFABuilder<Character>().withAlphabet(inputs) // input alphabet
.withOracle(mqOracle) // membership oracle
.create();
final DFAEquivalenceOracle<Character> eqOracle = new DFASimulatorEQOracle<>(target);
final LearningTask<DFA<?, Character>, Character, Boolean> learningTask =
new LearningTask<>(inputs, learner, eqOracle);
final ExecutorService executor = Executors.newSingleThreadExecutor();
final Future<DFA<?, Character>> future = executor.submit(learningTask);
try {
System.out.println("Started");
System.out.println(future.get(5, TimeUnit.SECONDS));
System.out.println("Finished!");
} catch (TimeoutException e) {
future.cancel(true);
System.out.println("Timeout!");
}
executor.shutdownNow();
final DFA<?, Character> result = learningTask.latestHyp;
Visualization.visualize(result, inputs);
}
static class LearningTask<A, I, D> implements Callable<A> {
private final Alphabet<I> alphabet;
private final LearningAlgorithm<A, I, D> learner;
private final EquivalenceOracle<A, I, D> eqOracle;
private A latestHyp;
public LearningTask(Alphabet<I> alphabet,
LearningAlgorithm<A, I, D> learner,
EquivalenceOracle<A, I, D> eqOracle) {
this.eqOracle = eqOracle;
this.learner = learner;
this.alphabet = alphabet;
}
@Override
public A call() throws Exception {
learner.startLearning();
latestHyp = learner.getHypothesisModel();
DefaultQuery<I, D> ce;
while ((ce = eqOracle.findCounterExample(latestHyp, alphabet)) != null) {
System.out.println("Found counterexample");
learner.refineHypothesis(ce);
latestHyp = learner.getHypothesisModel();
Thread.sleep(2000); // Just to demo a long running task of 2 seconds.
}
System.out.println("Finished");
return latestHyp;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment