|
|
using Implab;
|
|
|
using System;
|
|
|
using System.Collections.Generic;
|
|
|
using System.Diagnostics;
|
|
|
using System.Linq;
|
|
|
using System.Text;
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
|
namespace Implab.Automaton {
|
|
|
public abstract class DFAutomaton<T> {
|
|
|
protected struct ContextFrame {
|
|
|
public DFAStateDescriptior[] states;
|
|
|
public int current;
|
|
|
public T info;
|
|
|
}
|
|
|
|
|
|
public const int INITIAL_STATE = DFADefinition.INITIAL_STATE;
|
|
|
public const int UNREACHEBLE_STATE = DFADefinition.UNREACHEBLE_STATE;
|
|
|
|
|
|
protected ContextFrame m_context;
|
|
|
Stack<ContextFrame> m_contextStack = new Stack<ContextFrame>();
|
|
|
|
|
|
protected int Level {
|
|
|
get { return m_contextStack.Count; }
|
|
|
}
|
|
|
|
|
|
protected DFAutomaton(DFAStateDescriptior[] states, int startState, T info) {
|
|
|
Safe.ArgumentNotNull(states, "states");
|
|
|
Safe.ArgumentInRange(startState, 0, states.Length - 1, "startState");
|
|
|
|
|
|
m_context.states = states;
|
|
|
m_context.current = startState;
|
|
|
m_context.info = info;
|
|
|
}
|
|
|
|
|
|
protected void Switch(DFAStateDescriptior[] states, int current, T info) {
|
|
|
Debug.Assert(states != null);
|
|
|
Debug.Assert(current >= 0 && current < states.Length);
|
|
|
m_contextStack.Push(m_context);
|
|
|
m_context.states = states;
|
|
|
m_context.current = current;
|
|
|
m_context.info = info;
|
|
|
}
|
|
|
|
|
|
protected void Restore() {
|
|
|
Debug.Assert(m_contextStack.Count > 0);
|
|
|
|
|
|
m_context = m_contextStack.Pop();
|
|
|
}
|
|
|
|
|
|
protected void Move(int input) {
|
|
|
Debug.Assert(input > 0 && input < m_context.states[m_context.current].transitions.Length);
|
|
|
m_context.current = m_context.states[m_context.current].transitions[input];
|
|
|
}
|
|
|
|
|
|
protected bool CanMove(int input) {
|
|
|
Debug.Assert(input > 0 && input < m_context.states[m_context.current].transitions.Length);
|
|
|
return m_context.states[m_context.current].transitions[input] != UNREACHEBLE_STATE;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|