package context.arch.enactor; import java.util.ArrayList; import java.util.List; import be.ac.ulg.montefiore.run.jahmm.Observation; import be.ac.ulg.montefiore.run.jahmm.ObservationVector; import context.arch.discoverer.query.AbstractQueryItem; import context.arch.discoverer.query.HmmWrapper; import context.arch.intelligibility.hmm.HmmExplainer; //import context.arch.widget.SequenceWidget; /** * Only one EnactorReference allowed. * * @author Brian Y. Lim * */ public class HmmEnactor<O extends Observation> extends Enactor { protected HmmWrapper hmmWrapper; protected HmmEnactorReference<O> hmmER; protected List<String> outcomeValueSequence; protected List<String> inputsSequence; @SuppressWarnings("unchecked") // public HMMEnactor(Class<? extends SequenceWidget> inWidgetClass, public HmmEnactor(AbstractQueryItem<?,?> inWidgetSubscriptionQuery, AbstractQueryItem<?,?> outWidgetSubscriptionQuery, String outcomeName, HmmWrapper hmmWrapper, String shortId) { super(inWidgetSubscriptionQuery, outWidgetSubscriptionQuery, outcomeName, shortId); this.hmmWrapper = hmmWrapper; // set up explainer setExplainer(new HmmExplainer((HmmEnactor<ObservationVector>) this)); // set up for enactor reference hmmER = new HmmEnactorReference<O>(this); setReference(hmmER); } /** * Refers to HMMSupervised to get the outcome values instead of multiple EnactorReferences, which this does not have. * This returns the possible outcome values for each sequence step. */ @Override public List<String> getOutcomeValues() { return hmmWrapper.getOutcomeValues(); } public List<String> getOutcomeValueSequence() { if (outcomeValueSequence == null) { return new ArrayList<String>(); } // create copy so that the original data doesn't get mutated by some other process return new ArrayList<String>(outcomeValueSequence); } public void setOutcomeValueSequence(List<String> valueSequence) { this.outcomeValueSequence = valueSequence; new RuntimeException("setOutcomeValueSequence = " + valueSequence); } public List<String> getInputsSequence() { // create copy so that the original data doesn't get mutated by some other process return new ArrayList<String>(inputsSequence); } public void setInputsSequence(List<String> inputsSequence) { this.inputsSequence = inputsSequence; new RuntimeException("setInputsSequence = " + inputsSequence); } public int getSequenceLength() { return hmmWrapper.getSequenceLength(); } /** * Really this is now a setReference(EnactorReference er), * since HMMEnactor can only have one EnactorReference. * @param er * @return may be false if exceeded more than one EnactorReference, and would override existing one. * @see #setReference(EnactorReference) which subclasses should use instead */ @Override @Deprecated public void addReference(EnactorReference er) { // throw new InvalidMethodException("ClassifierEnactor can only take one EnactorReference. Use setEnactorReference(EnactorReference er) instead."); // too troublesome to throw exception, though that is good design. if (enactorReferences.size() >= 1) { enactorReferences.clear(); // remove previous entry } super.addReference(er); } @SuppressWarnings("deprecation") protected void setReference(HmmEnactorReference<O> er) { addReference(er); } public EnactorReference getReference() { return enactorReferences.values().iterator().next().get(0); // get the only (first) entry } public HmmWrapper getHMM() { return hmmWrapper; } @SuppressWarnings("unchecked") public List<O> getObservations() { return (List<O>) hmmWrapper.extractObservations(this.getInWidgetState()); } }