// --- private functions ---- /** Add a transition from DA states da_from to stuttered_state to for edge elem. * If the state does not yet exist in the DA, create it. * @param da_from the from state in the DA * @param to the target state * @param elem the edge label */ DA_State add_transition(DA_State da_from, TreeWithAcceptance to, APElement elem) { DA_State da_to = _state_mapper.find(to); if (da_to == null) { da_to = _da_result.newState(); to.generateAcceptance(da_to.acceptance()); if (_detailed_states) { // da_to.setDescription(to->toHTML()); } _state_mapper.add(to, da_to); _unprocessed.Push(new KeyValuePair <TreeWithAcceptance, DA_State>(to, da_to)); } #if STUTTERED_VERBOSE std::cerr << da_from->getName() << " -> " << da_to->getName() << std::endl; #endif da_from.edges().set(elem, da_to); return(da_to); }
/** Remove an edge */ public void removeEdge(APElement label) { if (get(label) == null) { throw new IllegalArgumentException("Trying to remove non-existing edge!"); } set(label, default(T)); }
//public void addEdgeDebug(int label, int to) //{ // if(_storageDebug[label] == null) // { // List<int> list = new List<int>(); // list.Add(to); // _storageDebug[label] = list; // } // else // { // _storageDebug[label].Add(to); // } //} /** Add an edge that doesn't already exist */ //public void addEdge(APElement label, BitSet to) {addEdge(label, to);} /** Add an edge that doesn't already exist */ public void addEdge(APElement label, T to) { if (get(label) != null) // { throw new IllegalArgumentException("Trying to add edge which already exists!"); } set(label, to); }
/** Get the target of the edge labeled with label*/ public T get(APElement label) { if (label.getBitSet() >= _arraySize) { throw new IndexOutOfBoundsException(""); //, } return(_storage[label.getBitSet()]); }
public void set(APElement label, T to) { if (label.getBitSet() >= _arraySize) { throw new IndexOutOfBoundsException(""); //IndexOutOfBoundsException, } _storage[label.getBitSet()] = to; }
/** Check for partial stutter insensitiveness using * the nba and the complement nba */ public void checkNBAs(NBA nba, NBA nba_complement) { APSet apset = nba.getAPSet_cp(); bool nba_is_smaller = (nba.size() < nba_complement.size()); //if (_printInfo) { // std::cerr << "Checking for insensitiveness" << std::endl; //} bool one_insensitive = false; bool all_insensitive = true; //for (APSet::element_iterator it=apset->all_elements_begin(); it!=apset->all_elements_end();++it) for (int it = apset.all_elements_begin(); it != apset.all_elements_end(); ++it) { APElement elem = new APElement(it); if (_partiallyInsensitive.get(it)) { // don't recheck something we already now is stutter insensitive one_insensitive = true; continue; } // if (_printInfo) { //std::cerr << "Checking " << elem.toString(*apset) << ": "; //std::cerr.flush(); // } bool insensitive; if (nba_is_smaller) { insensitive = is_stutter_insensitive(nba, nba_complement, elem); } else { insensitive = is_stutter_insensitive(nba_complement, nba, elem); } if (insensitive) { _partiallyInsensitive.set(it); one_insensitive = true; //if (_printInfo) { // std::cerr << "+" << std::endl; //} } else { all_insensitive = false; //if (_printInfo) { // std::cerr << "-" << std::endl; //} } } _hasCheckedNBAs = true; _partiallyStutterInsensitive = one_insensitive; }
/** Calculate the successor state. * @param from_state The from state * @param elem The edge label * @return result_t the shared_ptr of the successor state */ public ResultStateInterface <UnionState> delta(UnionState from_state, APElement elem) { DA_State state1_to = _da_1[from_state.da_state_1].edges().get(elem); DA_State state2_to = _da_2[from_state.da_state_2].edges().get(elem); UnionState to = createState(state1_to.getName(), state2_to.getName()); return(new UnionState_Result(to)); }
/** * Print the DA in DOT format to the output stream. * This functions expects that the DA is compact. * @param da_type a string specifying the type of automaton ("DRA", "DSA"). * @param out the output stream */ public Graph AutomatonToDot() { Graph g = new Graph("graph"); g.Directed = true; APSet ap_set = getAPSet(); Dictionary <int, string> stateToNumber = new Dictionary <int, string>(); for (int i_state = 0; i_state < this.size(); i_state++) { //out << "\"" << i_state << "\" ["; Node d = formatStateForDOT(i_state, g); stateToNumber.Add(i_state, d.Id); } //out << "]\n"; // close parameters for state for (int i_state = 0; i_state < this.size(); i_state++) { // transitions DA_State cur_state = this.get(i_state); if (cur_state.hasOnlySelfLoop()) { // get first to-state, as all the to-states are the same DA_State to = cur_state.edges().get(new APElement(ap_set.all_elements_begin())); //out << "\"" << i_state << "\" -> \"" << to->getName(); //out << "\" [label=\" true\", color=blue]\n"; Edge edge = g.AddEdge(stateToNumber[i_state], "\u03A3", stateToNumber[to.getName()]); //edge.Attr.Color = Color.Blue; } else { //for (APSet::element_iterator el_it=ap_set.all_elements_begin();el_it!=ap_set.all_elements_end();++el_it) for (int el_it = ap_set.all_elements_begin(); el_it != ap_set.all_elements_end(); ++el_it) { APElement label = new APElement(el_it); DA_State to_state = cur_state.edges().get(label); int to_state_index = to_state.getName(); //out << "\"" << i_state << "\" -> \"" << to_state_index; //out << "\" [label=\" " << label.toString(getAPSet(), false) << "\"]\n"; Edge edge = g.AddEdge(stateToNumber[i_state], label.toString(getAPSet(), false), stateToNumber[to_state_index]); //edge.Attr.Color = Color.Blue; } } } return(g); }
/** * Constructor that generates an iterator pointing * to a specific APElement. * @param ap_set the underlying APSet * @param m the APMonom over which we iterate * @param cur_e the current APElement */ public APMonom2APElements(APSet ap_set, APMonom m, APElement cur_e) { _ap_set = ap_set; _m = m; _cur_e = cur_e; _end_marker = false; if (m.isFalse()) { _end_marker = true; } }
/** * Constructor that generates an iterator pointing to the first * APElement. * @param ap_set the underlying APSet * @param m the APMonom over which we iterate */ public APMonom2APElements(APSet ap_set, APMonom m) { _ap_set = ap_set; _m = m; _cur_e = new APElement(m.getValueBits()); _end_marker = false; if (m.isFalse()) { _end_marker = true; } }
// -- private member functions /** Check that symbol label is stutter insensitive, * using nba and complement_nba */ public bool is_stutter_insensitive(NBA nba, NBA nba_complement, APElement label) { NBA stutter_closed_nba = NBAStutterClosure.stutter_closure(nba, label); NBA product = NBA.product_automaton(stutter_closed_nba, nba_complement); NBAAnalysis analysis_product = new NBAAnalysis(product); bool empty = analysis_product.emptinessCheck(); // std::cerr << "NBA is " << (empty ? "empty" : "not empty") << std::endl; return(empty); }
/** Constructor */ public SCC_DFS(NBA graph, SCCs result, APElement label) // { _graph = graph; _result = result; //_successor_access = successor_access; _labelMark = label; /** The DFS stack */ _stack = new Stack <int>(); /** The SCC_DFS_Data for every state (state index -> DFS_DATA) */ _dfs_data = new List <SCC_DFS_Data>(); }
/** Add an edge. */ public void addEdge(APMonom label, NBA_State state) { APSet ap_set = _state.getGraph().getAPSet(); APMonom2APElements start = APMonom2APElements.begin(ap_set, label); //for (APMonom2APElements it=APMonom2APElements::begin(ap_set, label);it!=APMonom2APElements::end(ap_set, label);++it) while (!start.equal(APMonom2APElements.end(ap_set, label)))///////////////***********note sth wrong here don't skip sth extra { APElement it = start._cur_e; addEdge(it, state); start.increment(); } }
/** Make this automaton into an never accepting automaton */ public void constructEmpty() { DA_State n = this.newState(); setStartState(n); //for (APSet::element_iterator it_elem= DA<Label,EdgeContainer,RabinAcceptance>::getAPSet().all_elements_begin();it_elem!=DA<Label,EdgeContainer,RabinAcceptance>::getAPSet().all_elements_end();++it_elem) APSet ap_set = getAPSet(); for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) { APElement label = new APElement(it_elem); n.edges().addEdge(label, n); } }
// --- private functions ---- /** Add a transition from DA states da_from to stuttered_state to for edge elem. * If the state does not yet exist in the DA, create it. * @param da_from the from state in the DA * @param to the target state * @param elem the edge label */ DA_State add_transition(DA_State da_from, TreeWithAcceptance to, APElement elem) { DA_State da_to = _state_mapper.find(to); if (da_to == null) { da_to = _da_result.newState(); to.generateAcceptance(da_to.acceptance()); if (_detailed_states) { // da_to.setDescription(to->toHTML()); } _state_mapper.add(to, da_to); _unprocessed.Push(new KeyValuePair<TreeWithAcceptance, DA_State>(to, da_to)); } #if STUTTERED_VERBOSE std::cerr << da_from->getName() << " -> " << da_to->getName() << std::endl; #endif da_from.edges().set(elem, da_to); return da_to; }
/** Calculate and add transitions to the successor state. * @param from the source stuttered_state * @param da_from the source DA state * @param elem the edge label */ void calc_delta(TreeWithAcceptance from, DA_State da_from, APElement elem) { //StateMapper<SafraTree, int , ptr_hash<algo_state_t>> intermediate_state_map_t; //, PtrComparator<algo_state_t> Dictionary<StateInterface, int> state_map = new Dictionary<StateInterface, int>(); List<StateInterface> state_vector = new List<StateInterface>(); StateInterface start_tree = from.getTree(); //state_map[start_tree] = null; state_map.Add(start_tree, 0); state_vector.Add(start_tree); //push_back #if STUTTERED_VERBOSE std::cerr << "Calculate from state [" << da_from->getName() << "], " << (unsigned int ) elem << ":" << std::endl; std::cerr << start_tree->toString() << std::endl; #endif StateInterface cur_tree = start_tree; while (true) { StateInterface next_tree = _algo.delta(cur_tree as UnionState, elem).getState(); //typename intermediate_state_map_t::iterator it; //int it = state_map.find(next_tree); //if (it == state_map.end()) if (!state_map.ContainsKey(next_tree)) { // tree doesn't yet exist... // add tree //state_map[next_tree] = state_vector.size(); state_map.Add(next_tree, state_vector.Count); state_vector.Add(next_tree); //push_back cur_tree = next_tree; continue; } else { // found the cycle! int cycle_point = state_map[next_tree]; #if STUTTERED_VERBOSE std::cerr << "-----------------------\n"; for (unsigned int i=0;i<state_vector.size();i++) { std::cerr << "[" << i << "] "; if (cycle_point==i) { std::cerr << "* "; } std::cerr << "\n" << state_vector[i]->toString() << std::endl; } std::cerr << "-----------------------\n"; #endif prefix_and_cycle_state_t pac = calculate_prefix_and_cycle_state(state_vector, cycle_point); //DA_State da_prefix = null; DA_State da_cycle = null; if (pac.prefix_state != null && !(pac.prefix_state == pac.cycle_state)) { DA_State da_prefix = add_transition(da_from, pac.prefix_state, elem); da_cycle = add_transition(da_prefix, pac.cycle_state, elem); } else { da_cycle = add_transition(da_from, pac.cycle_state, elem); } da_cycle.edges().set(elem, da_cycle); return; } } }
// -- private member functions /** Check that symbol label is stutter insensitive, * using nba and complement_nba */ public bool is_stutter_insensitive(NBA nba, NBA nba_complement, APElement label) { NBA stutter_closed_nba = NBAStutterClosure.stutter_closure(nba, label); NBA product = NBA.product_automaton(stutter_closed_nba, nba_complement); NBAAnalysis analysis_product = new NBAAnalysis(product); bool empty = analysis_product.emptinessCheck(); // std::cerr << "NBA is " << (empty ? "empty" : "not empty") << std::endl; return empty; }
//, SuccessorAccess& successor_access /** Calculate the SCCs for Graph graph and save in result. */ public static void calculateSCCs(NBA graph, SCCs result, bool disjoint, APElement label) { SCC_DFS scc_dfs = new SCC_DFS(graph, result, label); scc_dfs.calculate(disjoint); }
///** Destructor */ //~NBA_State_EdgeManager() { // const APSet& ap_set=_state.getGraph().getAPSet(); // for (APSet::element_iterator eit=ap_set.all_elements_begin(); // eit!=ap_set.all_elements_end(); // ++eit) { // delete _container.get(*eit); // } //} /** Get the target states */ public BitSet getEdge(APElement label) { return _container.get(label); }
/** * Add an edge from this state to the other state * @param label the label for the edge * @param state the target state */ public void addEdge(APElement label, NBA_State state) { _edge_manager.addEdge(label, state); }
/** Calculate the stutter closure for the NBA, for a certain symbol. * @param nba the NBA * @param label the symbol for which to perform the stutter closure */ public static NBA stutter_closure(NBA nba, APElement label) { APSet apset = nba.getAPSet_cp(); NBA nba_result_ptr = new NBA(apset); NBA result = nba_result_ptr; int element_count = apset.powersetSize(); Debug.Assert(nba.getStartState() != null); int start_state = nba.getStartState().getName(); for (int i = 0; i < nba.size(); i++) { int st = result.nba_i_newState(); Debug.Assert(st == i); if (st == start_state) { result.setStartState(result[st]); } if (nba[st].isFinal()) { result[st].setFinal(true); } } for (int i = 0; i < nba.size(); i++) { int st = result.nba_i_newState(); Debug.Assert(st == nba.size() + i); result[st].addEdge(label, result[i]); result[st].addEdge(label, result[st]); } //List<BitSet> reachable = null; //NBAEdgeSuccessors edge_successor = new NBAEdgeSuccessors(label); SCCs scc = new SCCs(); GraphAlgorithms.calculateSCCs(nba, scc, true, label); //,edge_successor List<BitSet> reachable = scc.getReachabilityForAllStates(); // std::cerr << "SCCs for " << label.toString(*apset) << std::endl; // std::cerr << scc << std::endl; // std::cerr << " Reachability: "<< std::endl; // for (unsigned int t=0; t < reachable->size(); t++) { // std::cerr << t << " -> " << (*reachable)[t] << std::endl; // } // std::cerr << " ---\n"; for (int i = 0; i < nba.size(); i++) { NBA_State from = result[i]; for (int j = 0; j < element_count; j++) { BitSet result_to = new BitSet(); BitSet to = nba[i].getEdge(new APElement(j)); if (j != label.bitset) { result_to = to; } else { //for (BitSetIterator it=BitSetIterator(*to);it!=BitSetIterator::end(*to);++it) for (int it = BitSetIterator.start(to); it != BitSetIterator.end(to); it = BitSetIterator.increment(to, it)) { int to_state = it; // We can go directly to the original state result_to.set(to_state); // We can also go to the corresponding stutter state instead int stutter_state = nba.size() + to_state; result_to.set(stutter_state); // ... and then we can go directly to all the states that are j-reachable from to result_to.Union(reachable[to_state]); } } from.getEdge(new APElement(j)).Assign(result_to); } } //delete reachable; return nba_result_ptr; }
/** * Generate a DA using the Algorithm * Throws LimitReachedException if a limit is set (>0) and * there are more states in the generated DA than the limit. * @param algo the algorithm * @param da_result the DA where the result is stored * (has to have same APSet as the nba) * @param limit a limit for the number of states (0 disables the limit). */ public void convert(SafraAlgorithm algo, DRA da_result, int limit) { /** The hash map from DA_State to StateInterface */ StateMapper <StateInterface, DA_State> state_mapper = new StateMapper <StateInterface, DA_State>(); APSet ap_set = da_result.getAPSet();////////////************where dose this dra have ap_set? if (algo.checkEmpty()) { da_result.constructEmpty(); return; } //typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; //* Creates new acceptance pairs according to da_result's acceptance. algo.prepareAcceptance(da_result.acceptance());////*********don't understand well StateInterface start = algo.getStartState(); DA_State start_state = da_result.newState();/////************?? what is in this newState? start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { start_state.setDescription(start.toHTML()); } state_mapper.add(start, start_state); da_result.setStartState(start_state); //typedef std::pair<algo_state_t, da_state_t*> unprocessed_value; Stack <KeyValuePair <StateInterface, DA_State> > unprocessed = new Stack <KeyValuePair <StateInterface, DA_State> >(); unprocessed.Push(new KeyValuePair <StateInterface, DA_State>(start, start_state)); while (unprocessed.Count > 0) { KeyValuePair <StateInterface, DA_State> top = unprocessed.Pop(); //unprocessed.pop(); StateInterface cur = top.Key; //safratreeNode DA_State from = top.Value; //DA_state //for (APSet::element_iterator it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) ///from 0 to 2^ap_set.size { APElement elem = new APElement(it_elem); /////////set simpleBitset = it_elem ResultStateInterface <SafraTree> result = algo.delta(cur as SafraTree, elem); /////get a new safraTree through elem DA_State to = state_mapper.find(result.getState()); if (to == null)////////////////result is not in state mapper. { to = da_result.newState(); result.getState().generateAcceptance(to.acceptance()); if (_detailed_states) { to.setDescription(result.getState().toHTML()); } state_mapper.add(result.getState(), to); unprocessed.Push(new KeyValuePair <StateInterface, DA_State>(result.getState(), to)); } from.edges().set(elem, to);//////////////add this edge. if (limit != 0 && da_result.size() > limit) { throw new LimitReachedException(""); } } } }
//typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; //typedef TreeWithAcceptance<algo_state_t, typename Acceptance::signature_type> stuttered_state_t; //typedef typename stuttered_state_t::ptr stuttered_state_ptr_t; //typedef std::pair<stuttered_state_ptr_t, da_state_t*> unprocessed_value_t; //typedef std::stack<unprocessed_value_t> unprocessed_stack_t; /** Convert the NBA to the DA */ public void convert() { APSet ap_set = _da_result.getAPSet(); if (_algo.checkEmpty()) { _da_result.constructEmpty(); return; } _algo.prepareAcceptance(_da_result.acceptance()); TreeWithAcceptance s_start = new TreeWithAcceptance(_algo.getStartState()); DA_State start_state = _da_result.newState(); s_start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { //start_state->setDescription(s_start->toHTML()); start_state.setDescription("hahahahah"); } _state_mapper.add(s_start, start_state); _da_result.setStartState(start_state); Stack<KeyValuePair<TreeWithAcceptance, DA_State>> unprocessed; _unprocessed.Push(new KeyValuePair<TreeWithAcceptance, DA_State>(s_start, start_state)); bool all_insensitive = _stutter_information.isCompletelyInsensitive(); BitSet partial_insensitive = _stutter_information.getPartiallyInsensitiveSymbols(); while (_unprocessed.Count > 0) { KeyValuePair<TreeWithAcceptance, DA_State> top = _unprocessed.Pop(); //_unprocessed.pop(); TreeWithAcceptance from = top.Key; DA_State da_from = top.Value; //for (APSet::element_iterator it_elem=ap_set.all_elements_begin();it_elem!=ap_set.all_elements_end();++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) { APElement elem = new APElement(it_elem); if (da_from.edges().get(elem) == null) { // the edge was not yet calculated... if (!all_insensitive && partial_insensitive.get(it_elem) == null) { // can't stutter for this symbol, do normal step UnionState next_tree = _algo.delta(from.getTree() as UnionState, elem).getState(); TreeWithAcceptance next_state = new TreeWithAcceptance(next_tree); add_transition(da_from, next_state, elem); continue; } // normal stuttering... calc_delta(from, da_from, elem); if (_limit != 0 && _da_result.size() > _limit) { //THROW_EXCEPTION(LimitReachedException, ""); throw new Exception("LimitReachedException"); } } } } }
/** * Constructor. */ public STVisitor_powerset(NBA nba, APElement elem) { _nba = nba; _elem = elem; }
public static NBA product_automaton(NBA nba_1, NBA nba_2) { Debug.Assert(nba_1.getAPSet() == nba_2.getAPSet()); NBA product_nba = new NBA(nba_1.getAPSet_cp()); APSet apset = nba_1.getAPSet(); Debug.Assert(apset == nba_2.getAPSet()); for (int s_1 = 0; s_1 < nba_1.size(); s_1++) { for (int s_2 = 0; s_2 < nba_2.size(); s_2++) { for (int copy = 0; copy < 2; copy++) { int s_r = product_nba.nba_i_newState(); Debug.Assert(s_r == (s_1 * nba_2.size() + s_2) * 2 + copy); int to_copy = copy; if (copy == 0 && nba_1[s_1].isFinal()) { to_copy = 1; } if (copy == 1 && nba_2[s_2].isFinal()) { product_nba[s_r].setFinal(true); to_copy = 0; } //for (typename APSet::element_iterator it=apset.all_elements_begin();it!=apset.all_elements_end();++it) for (int it = apset.all_elements_begin(); it != apset.all_elements_end(); it++) { APElement label = new APElement(it); BitSet to_s1 = nba_1[s_1].getEdge(label); BitSet to_s2 = nba_2[s_2].getEdge(label); BitSet to_set = new BitSet(); //for (BitSetIterator it_e_1 = BitSetIterator(*to_s1); it_e_1 != BitSetIterator::end(*to_s1); ++it_e_1) //for (int it_e_1 = 0; it_e_1 != to_s1.bitset.Count; ++it_e_1) for (int it_e_1 = BitSetIterator.start(to_s1); it_e_1 != BitSetIterator.end(to_s1); it_e_1 = BitSetIterator.increment(to_s1, it_e_1)) { //for (BitSetIterator it_e_2 = BitSetIterator(*to_s2); it_e_2 != BitSetIterator::end(*to_s2); ++it_e_2) //for (int it_e_2 = 0; it_e_2 != to_s2.bitset.Count; ++it_e_2) for (int it_e_2 = BitSetIterator.start(to_s2); it_e_2 != BitSetIterator.end(to_s2); it_e_2 = BitSetIterator.increment(to_s2, it_e_2)) { int to = it_e_1 * nba_2.size() + it_e_2 * 2 + to_copy; to_set.set(to); } } product_nba[s_r].getEdge(label).Assign(to_set); } } } } int start_1 = nba_1.getStartState().getName(); int start_2 = nba_2.getStartState().getName(); product_nba.setStartState(product_nba[start_1 * nba_2.size() + start_2]); return product_nba; }
/* * edge_container_type& edges() {return _edges;} * const edge_container_type& edges() const {return _edges;} */ /** * Get the target states of the labeled edge. * @return a pointer to a BitSet with the indizes of the target states. */ public BitSet getEdge(APElement label) { return(_edge_manager.getEdge(label)); }
/** Calculate the SCCs for Graph graph and save in result. */ //public static void calculateSCCs(NBA graph, SCCs result) //{ // calculateSCCs(graph, result, false); //} /** Calculate the SCCs for Graph graph and save in result. */ public static void calculateSCCs(NBA graph, SCCs result, bool disjoint, APElement label) { // =false, SuccessorAccess successor_access=SuccessorAccess() SCC_DFS.calculateSCCs(graph, result, disjoint, label); //, successor_access }
/** Calculate the SCCs for Graph graph and save in result. */ public static void calculateSCCs(NBA graph, SCCs result, bool disjoint, APElement label) //, SuccessorAccess& successor_access { SCC_DFS scc_dfs = new SCC_DFS(graph, result, label); scc_dfs.calculate(disjoint); }
/** Calculate the stutter closure for the NBA, for a certain symbol. * @param nba the NBA * @param label the symbol for which to perform the stutter closure */ public static NBA stutter_closure(NBA nba, APElement label) { APSet apset = nba.getAPSet_cp(); NBA nba_result_ptr = new NBA(apset); NBA result = nba_result_ptr; int element_count = apset.powersetSize(); Debug.Assert(nba.getStartState() != null); int start_state = nba.getStartState().getName(); for (int i = 0; i < nba.size(); i++) { int st = result.nba_i_newState(); Debug.Assert(st == i); if (st == start_state) { result.setStartState(result[st]); } if (nba[st].isFinal()) { result[st].setFinal(true); } } for (int i = 0; i < nba.size(); i++) { int st = result.nba_i_newState(); Debug.Assert(st == nba.size() + i); result[st].addEdge(label, result[i]); result[st].addEdge(label, result[st]); } //List<BitSet> reachable = null; //NBAEdgeSuccessors edge_successor = new NBAEdgeSuccessors(label); SCCs scc = new SCCs(); GraphAlgorithms.calculateSCCs(nba, scc, true, label); //,edge_successor List <BitSet> reachable = scc.getReachabilityForAllStates(); // std::cerr << "SCCs for " << label.toString(*apset) << std::endl; // std::cerr << scc << std::endl; // std::cerr << " Reachability: "<< std::endl; // for (unsigned int t=0; t < reachable->size(); t++) { // std::cerr << t << " -> " << (*reachable)[t] << std::endl; // } // std::cerr << " ---\n"; for (int i = 0; i < nba.size(); i++) { NBA_State from = result[i]; for (int j = 0; j < element_count; j++) { BitSet result_to = new BitSet(); BitSet to = nba[i].getEdge(new APElement(j)); if (j != label.bitset) { result_to = to; } else { //for (BitSetIterator it=BitSetIterator(*to);it!=BitSetIterator::end(*to);++it) for (int it = BitSetIterator.start(to); it != BitSetIterator.end(to); it = BitSetIterator.increment(to, it)) { int to_state = it; // We can go directly to the original state result_to.set(to_state); // We can also go to the corresponding stutter state instead int stutter_state = nba.size() + to_state; result_to.set(stutter_state); // ... and then we can go directly to all the states that are j-reachable from to result_to.Union(reachable[to_state]); } } from.getEdge(new APElement(j)).Assign(result_to); } } //delete reachable; return(nba_result_ptr); }
///** Get the target states */ //public BitSet getEdge(APMonom monom) { // throw new Exception("Not implemented!"); //} /** Add an edge. */ public void addEdge(APElement label, NBA_State state) { _container.get(label).set(state.getName());///////////////note here //_container.addEdgeDebug(label.getBitSet(), state.getName()); }
///** Destructor */ //~NBA_State_EdgeManager() { // const APSet& ap_set=_state.getGraph().getAPSet(); // for (APSet::element_iterator eit=ap_set.all_elements_begin(); // eit!=ap_set.all_elements_end(); // ++eit) { // delete _container.get(*eit); // } //} /** Get the target states */ public BitSet getEdge(APElement label) { return(_container.get(label)); }
public List<int> MakeOneMove(int stateIndex, Valuation env, string evt) { DA_State state = this._index[stateIndex]; List<int> returnList = new List<int>(); if (state.hasOnlySelfLoop()) { // get first to-state, as all the to-states are the same DA_State to = state.edges().get(new APElement(_ap_set.all_elements_begin())); returnList.Add(to.Index); return returnList; } //Transition[] trans = fromTransitions[state]; //foreach (Transition tran in trans) for (int el_it = _ap_set.all_elements_begin(); el_it != _ap_set.all_elements_end(); ++el_it) { APElement label = new APElement(el_it); DA_State to_state = state.edges().get(label); int to_state_index = to_state.Index; //bool toAdd = true; //for (int i = 0; i < _ap_set.size(); i++) bool toAdd = true; for (int i = 0; i < _ap_set.size(); i++) { ////If the transition is labelled with Sigma, there should not be any other labels. //if (label.IsSigmal) //{ // //if(!returnList.Contains(tran.ToState)) // { // returnList.Add(tran.ToState); // } // break; //} string labelstring = _ap_set.getAP(i); //If the labed is negated, e.g., !eat0. if (!label.get(i)) { if (!DeclarationDatabase.ContainsKey(labelstring)) //If the label is an event. { //if the label says that this event can not happen, the event is eat0 and the label is !eat0. if (labelstring == evt) { toAdd = false; break; } } else //If the label is a proposition. { ExpressionValue v = EvaluatorDenotational.Evaluate(DeclarationDatabase[labelstring], env); //liuyang: v must be a boolconstant, 20/04/2009 Debug.Assert(v is BoolConstant); //if (v is BoolConstant) //{ if ((v as BoolConstant).Value) { toAdd = false; break; } //} } } else //if (!label.Negated) { if (!DeclarationDatabase.ContainsKey(labelstring)) //If the label is an event. { if (labelstring != evt) { toAdd = false; break; } } else //If the label is a proposition. { ExpressionValue v = EvaluatorDenotational.Evaluate(DeclarationDatabase[labelstring], env); //liuyang: v must be a boolconstant, 20/04/2009 Debug.Assert(v is BoolConstant); //if (v is BoolConstant) //{ if (!(v as BoolConstant).Value) { toAdd = false; break; } //} } } } if (toAdd && !returnList.Contains(to_state_index)) { returnList.Add(to_state_index); } } return returnList; }
/** * Generate a DA using the Algorithm * Throws LimitReachedException if a limit is set (>0) and * there are more states in the generated DA than the limit. * @param algo the algorithm * @param da_result the DA where the result is stored * (has to have same APSet as the nba) * @param limit a limit for the number of states (0 disables the limit). */ public void convert(DAUnionAlgorithm algo, DRA da_result, int limit) { StateMapper <StateInterface, DA_State> state_mapper = new StateMapper <StateInterface, DA_State>(); APSet ap_set = da_result.getAPSet(); if (algo.checkEmpty()) { da_result.constructEmpty(); return; } //typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; algo.prepareAcceptance(da_result.acceptance()); StateInterface start = algo.getStartState(); DA_State start_state = da_result.newState(); start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { start_state.setDescription(start.toHTML()); } state_mapper.add(start, start_state); da_result.setStartState(start_state); //typedef std::pair<algo_state_t, da_state_t*> unprocessed_value; Stack <KeyValuePair <StateInterface, DA_State> > unprocessed = new Stack <KeyValuePair <StateInterface, DA_State> >(); unprocessed.Push(new KeyValuePair <StateInterface, DA_State>(start, start_state)); while (unprocessed.Count > 0) { KeyValuePair <StateInterface, DA_State> top = unprocessed.Pop(); //unprocessed.pop(); StateInterface cur = top.Key; DA_State from = top.Value; //for (APSet::element_iterator it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) { APElement elem = new APElement(it_elem); ResultStateInterface <UnionState> result = algo.delta(cur as UnionState, elem); DA_State to = state_mapper.find(result.getState()); if (to == null) { to = da_result.newState(); result.getState().generateAcceptance(to.acceptance()); if (_detailed_states) { to.setDescription(result.getState().toHTML()); } state_mapper.add(result.getState(), to); unprocessed.Push(new KeyValuePair <StateInterface, DA_State>(result.getState(), to)); } from.edges().set(elem, to); if (limit != 0 && da_result.size() > limit) { throw new LimitReachedException(""); } } } }
public static NBA product_automaton(NBA nba_1, NBA nba_2) { Debug.Assert(nba_1.getAPSet() == nba_2.getAPSet()); NBA product_nba = new NBA(nba_1.getAPSet_cp()); APSet apset = nba_1.getAPSet(); Debug.Assert(apset == nba_2.getAPSet()); for (int s_1 = 0; s_1 < nba_1.size(); s_1++) { for (int s_2 = 0; s_2 < nba_2.size(); s_2++) { for (int copy = 0; copy < 2; copy++) { int s_r = product_nba.nba_i_newState(); Debug.Assert(s_r == (s_1 * nba_2.size() + s_2) * 2 + copy); int to_copy = copy; if (copy == 0 && nba_1[s_1].isFinal()) { to_copy = 1; } if (copy == 1 && nba_2[s_2].isFinal()) { product_nba[s_r].setFinal(true); to_copy = 0; } //for (typename APSet::element_iterator it=apset.all_elements_begin();it!=apset.all_elements_end();++it) for (int it = apset.all_elements_begin(); it != apset.all_elements_end(); it++) { APElement label = new APElement(it); BitSet to_s1 = nba_1[s_1].getEdge(label); BitSet to_s2 = nba_2[s_2].getEdge(label); BitSet to_set = new BitSet(); //for (BitSetIterator it_e_1 = BitSetIterator(*to_s1); it_e_1 != BitSetIterator::end(*to_s1); ++it_e_1) //for (int it_e_1 = 0; it_e_1 != to_s1.bitset.Count; ++it_e_1) for (int it_e_1 = BitSetIterator.start(to_s1); it_e_1 != BitSetIterator.end(to_s1); it_e_1 = BitSetIterator.increment(to_s1, it_e_1)) { //for (BitSetIterator it_e_2 = BitSetIterator(*to_s2); it_e_2 != BitSetIterator::end(*to_s2); ++it_e_2) //for (int it_e_2 = 0; it_e_2 != to_s2.bitset.Count; ++it_e_2) for (int it_e_2 = BitSetIterator.start(to_s2); it_e_2 != BitSetIterator.end(to_s2); it_e_2 = BitSetIterator.increment(to_s2, it_e_2)) { int to = it_e_1 * nba_2.size() + it_e_2 * 2 + to_copy; to_set.set(to); } } product_nba[s_r].getEdge(label).Assign(to_set); } } } } int start_1 = nba_1.getStartState().getName(); int start_2 = nba_2.getStartState().getName(); product_nba.setStartState(product_nba[start_1 * nba_2.size() + start_2]); return(product_nba); }
/** * Print the DA in DOT format to the output stream. * This functions expects that the DA is compact. * @param da_type a string specifying the type of automaton ("DRA", "DSA"). * @param out the output stream */ public Graph AutomatonToDot() { Graph g = new Graph("graph"); g.Directed = true; APSet ap_set = getAPSet(); Dictionary<int, string> stateToNumber = new Dictionary<int, string>(); for (int i_state = 0; i_state < this.size(); i_state++) { //out << "\"" << i_state << "\" ["; Node d = formatStateForDOT(i_state, g); stateToNumber.Add(i_state, d.Id); } //out << "]\n"; // close parameters for state for (int i_state = 0; i_state < this.size(); i_state++) { // transitions DA_State cur_state = this.get(i_state); if (cur_state.hasOnlySelfLoop()) { // get first to-state, as all the to-states are the same DA_State to = cur_state.edges().get(new APElement(ap_set.all_elements_begin())); //out << "\"" << i_state << "\" -> \"" << to->getName(); //out << "\" [label=\" true\", color=blue]\n"; Edge edge = g.AddEdge(stateToNumber[i_state], "\u03A3", stateToNumber[to.getName()]); //edge.Attr.Color = Color.Blue; } else { //for (APSet::element_iterator el_it=ap_set.all_elements_begin();el_it!=ap_set.all_elements_end();++el_it) for (int el_it = ap_set.all_elements_begin(); el_it != ap_set.all_elements_end(); ++el_it) { APElement label = new APElement(el_it); DA_State to_state = cur_state.edges().get(label); int to_state_index = to_state.getName(); //out << "\"" << i_state << "\" -> \"" << to_state_index; //out << "\" [label=\" " << label.toString(getAPSet(), false) << "\"]\n"; Edge edge = g.AddEdge(stateToNumber[i_state], label.toString(getAPSet(), false), stateToNumber[to_state_index]); //edge.Attr.Color = Color.Blue; } } } return g; }
// /** Constructor */ public SCC_DFS(NBA graph, SCCs result, APElement label) { _graph = graph; _result = result; //_successor_access = successor_access; _labelMark = label; /** The DFS stack */ _stack = new Stack<int>(); /** The SCC_DFS_Data for every state (state index -> DFS_DATA) */ _dfs_data = new List<SCC_DFS_Data>(); }
/* edge_container_type& edges() {return _edges;} const edge_container_type& edges() const {return _edges;} */ /** * Get the target states of the labeled edge. * @return a pointer to a BitSet with the indizes of the target states. */ public BitSet getEdge(APElement label) { return _edge_manager.getEdge(label); }
public List <int> MakeOneMove(int stateIndex, Valuation env, string evt) { DA_State state = this._index[stateIndex]; List <int> returnList = new List <int>(); if (state.hasOnlySelfLoop()) { // get first to-state, as all the to-states are the same DA_State to = state.edges().get(new APElement(_ap_set.all_elements_begin())); returnList.Add(to.Index); return(returnList); } //Transition[] trans = fromTransitions[state]; //foreach (Transition tran in trans) for (int el_it = _ap_set.all_elements_begin(); el_it != _ap_set.all_elements_end(); ++el_it) { APElement label = new APElement(el_it); DA_State to_state = state.edges().get(label); int to_state_index = to_state.Index; //bool toAdd = true; //for (int i = 0; i < _ap_set.size(); i++) bool toAdd = true; for (int i = 0; i < _ap_set.size(); i++) { ////If the transition is labelled with Sigma, there should not be any other labels. //if (label.IsSigmal) //{ // //if(!returnList.Contains(tran.ToState)) // { // returnList.Add(tran.ToState); // } // break; //} string labelstring = _ap_set.getAP(i); //If the labed is negated, e.g., !eat0. if (!label.get(i)) { if (!DeclarationDatabase.ContainsKey(labelstring)) //If the label is an event. { //if the label says that this event can not happen, the event is eat0 and the label is !eat0. if (labelstring == evt) { toAdd = false; break; } } else //If the label is a proposition. { ExpressionValue v = EvaluatorDenotational.Evaluate(DeclarationDatabase[labelstring], env); //liuyang: v must be a boolconstant, 20/04/2009 Debug.Assert(v is BoolConstant); //if (v is BoolConstant) //{ if ((v as BoolConstant).Value) { toAdd = false; break; } //} } } else //if (!label.Negated) { if (!DeclarationDatabase.ContainsKey(labelstring)) //If the label is an event. { if (labelstring != evt) { toAdd = false; break; } } else //If the label is a proposition. { ExpressionValue v = EvaluatorDenotational.Evaluate(DeclarationDatabase[labelstring], env); //liuyang: v must be a boolconstant, 20/04/2009 Debug.Assert(v is BoolConstant); //if (v is BoolConstant) //{ if (!(v as BoolConstant).Value) { toAdd = false; break; } //} } } } if (toAdd && !returnList.Contains(to_state_index)) { returnList.Add(to_state_index); } } return(returnList); }
/** * Generate a DA using the Algorithm * Throws LimitReachedException if a limit is set (>0) and * there are more states in the generated DA than the limit. * @param algo the algorithm * @param da_result the DA where the result is stored * (has to have same APSet as the nba) * @param limit a limit for the number of states (0 disables the limit). */ public void convert(DAUnionAlgorithm algo, DRA da_result, int limit) { StateMapper<StateInterface, DA_State> state_mapper = new StateMapper<StateInterface, DA_State>(); APSet ap_set = da_result.getAPSet(); if (algo.checkEmpty()) { da_result.constructEmpty(); return; } //typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; algo.prepareAcceptance(da_result.acceptance()); StateInterface start = algo.getStartState(); DA_State start_state = da_result.newState(); start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { start_state.setDescription(start.toHTML()); } state_mapper.add(start, start_state); da_result.setStartState(start_state); //typedef std::pair<algo_state_t, da_state_t*> unprocessed_value; Stack<KeyValuePair<StateInterface, DA_State>> unprocessed = new Stack<KeyValuePair<StateInterface, DA_State>>(); unprocessed.Push(new KeyValuePair<StateInterface, DA_State>(start, start_state)); while (unprocessed.Count > 0) { KeyValuePair<StateInterface, DA_State> top = unprocessed.Pop(); //unprocessed.pop(); StateInterface cur = top.Key; DA_State from = top.Value; //for (APSet::element_iterator it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) { APElement elem = new APElement(it_elem); ResultStateInterface<UnionState> result = algo.delta(cur as UnionState, elem); DA_State to = state_mapper.find(result.getState()); if (to == null) { to = da_result.newState(); result.getState().generateAcceptance(to.acceptance()); if (_detailed_states) { to.setDescription(result.getState().toHTML()); } state_mapper.add(result.getState(), to); unprocessed.Push(new KeyValuePair<StateInterface, DA_State>(result.getState(), to)); } from.edges().set(elem, to); if (limit != 0 && da_result.size() > limit) { throw new LimitReachedException(""); } } } }
//typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; //typedef TreeWithAcceptance<algo_state_t, typename Acceptance::signature_type> stuttered_state_t; //typedef typename stuttered_state_t::ptr stuttered_state_ptr_t; //typedef std::pair<stuttered_state_ptr_t, da_state_t*> unprocessed_value_t; //typedef std::stack<unprocessed_value_t> unprocessed_stack_t; /** Convert the NBA to the DA */ public void convert() { APSet ap_set = _da_result.getAPSet(); if (_algo.checkEmpty()) { _da_result.constructEmpty(); return; } _algo.prepareAcceptance(_da_result.acceptance()); TreeWithAcceptance s_start = new TreeWithAcceptance(_algo.getStartState()); DA_State start_state = _da_result.newState(); s_start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { //start_state->setDescription(s_start->toHTML()); start_state.setDescription("hahahahah"); } _state_mapper.add(s_start, start_state); _da_result.setStartState(start_state); Stack <KeyValuePair <TreeWithAcceptance, DA_State> > unprocessed; _unprocessed.Push(new KeyValuePair <TreeWithAcceptance, DA_State>(s_start, start_state)); bool all_insensitive = _stutter_information.isCompletelyInsensitive(); BitSet partial_insensitive = _stutter_information.getPartiallyInsensitiveSymbols(); while (_unprocessed.Count > 0) { KeyValuePair <TreeWithAcceptance, DA_State> top = _unprocessed.Pop(); //_unprocessed.pop(); TreeWithAcceptance from = top.Key; DA_State da_from = top.Value; //for (APSet::element_iterator it_elem=ap_set.all_elements_begin();it_elem!=ap_set.all_elements_end();++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) { APElement elem = new APElement(it_elem); if (da_from.edges().get(elem) == null) { // the edge was not yet calculated... if (!all_insensitive && partial_insensitive.get(it_elem) == null) { // can't stutter for this symbol, do normal step UnionState next_tree = _algo.delta(from.getTree() as UnionState, elem).getState(); TreeWithAcceptance next_state = new TreeWithAcceptance(next_tree); add_transition(da_from, next_state, elem); continue; } // normal stuttering... calc_delta(from, da_from, elem); if (_limit != 0 && _da_result.size() > _limit) { //THROW_EXCEPTION(LimitReachedException, ""); throw new Exception("LimitReachedException"); } } } } }
/** * Generate a DA using the Algorithm * Throws LimitReachedException if a limit is set (>0) and * there are more states in the generated DA than the limit. * @param algo the algorithm * @param da_result the DA where the result is stored * (has to have same APSet as the nba) * @param limit a limit for the number of states (0 disables the limit). */ public void convert(SafraAlgorithm algo, DRA da_result, int limit) { /** The hash map from DA_State to StateInterface */ StateMapper<StateInterface, DA_State> state_mapper = new StateMapper<StateInterface, DA_State>(); APSet ap_set = da_result.getAPSet();////////////************where dose this dra have ap_set? if (algo.checkEmpty()) { da_result.constructEmpty(); return; } //typedef typename DA_t::state_type da_state_t; //typedef typename Algorithm_t::state_t algo_state_t; //typedef typename Algorithm_t::result_t algo_result_t; //* Creates new acceptance pairs according to da_result's acceptance. algo.prepareAcceptance(da_result.acceptance());////*********don't understand well StateInterface start = algo.getStartState(); DA_State start_state = da_result.newState();/////************?? what is in this newState? start.generateAcceptance(start_state.acceptance()); if (_detailed_states) { start_state.setDescription(start.toHTML()); } state_mapper.add(start, start_state); da_result.setStartState(start_state); //typedef std::pair<algo_state_t, da_state_t*> unprocessed_value; Stack<KeyValuePair<StateInterface, DA_State>> unprocessed = new Stack<KeyValuePair<StateInterface, DA_State>>(); unprocessed.Push(new KeyValuePair<StateInterface, DA_State>(start, start_state)); while (unprocessed.Count > 0) { KeyValuePair<StateInterface, DA_State> top = unprocessed.Pop(); //unprocessed.pop(); StateInterface cur = top.Key;//safratreeNode DA_State from = top.Value;//DA_state //for (APSet::element_iterator it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem) for (int it_elem = ap_set.all_elements_begin(); it_elem != ap_set.all_elements_end(); ++it_elem)///from 0 to 2^ap_set.size { APElement elem = new APElement(it_elem);/////////set simpleBitset = it_elem ResultStateInterface<SafraTree> result = algo.delta(cur as SafraTree, elem);/////get a new safraTree through elem DA_State to = state_mapper.find(result.getState()); if (to == null)////////////////result is not in state mapper. { to = da_result.newState(); result.getState().generateAcceptance(to.acceptance()); if (_detailed_states) { to.setDescription(result.getState().toHTML()); } state_mapper.add(result.getState(), to); unprocessed.Push(new KeyValuePair<StateInterface, DA_State>(result.getState(), to)); } from.edges().set(elem, to);//////////////add this edge. if (limit != 0 && da_result.size() > limit) { throw new LimitReachedException(""); } } } }
/** Calculate and add transitions to the successor state. * @param from the source stuttered_state * @param da_from the source DA state * @param elem the edge label */ void calc_delta(TreeWithAcceptance from, DA_State da_from, APElement elem) { //StateMapper<SafraTree, int , ptr_hash<algo_state_t>> intermediate_state_map_t; //, PtrComparator<algo_state_t> Dictionary <StateInterface, int> state_map = new Dictionary <StateInterface, int>(); List <StateInterface> state_vector = new List <StateInterface>(); StateInterface start_tree = from.getTree(); //state_map[start_tree] = null; state_map.Add(start_tree, 0); state_vector.Add(start_tree); //push_back #if STUTTERED_VERBOSE std::cerr << "Calculate from state [" << da_from->getName() << "], " << (unsigned int ) elem << ":" << std::endl; std::cerr << start_tree->toString() << std::endl; #endif StateInterface cur_tree = start_tree; while (true) { StateInterface next_tree = _algo.delta(cur_tree as UnionState, elem).getState(); //typename intermediate_state_map_t::iterator it; //int it = state_map.find(next_tree); //if (it == state_map.end()) if (!state_map.ContainsKey(next_tree)) { // tree doesn't yet exist... // add tree //state_map[next_tree] = state_vector.size(); state_map.Add(next_tree, state_vector.Count); state_vector.Add(next_tree); //push_back cur_tree = next_tree; continue; } else { // found the cycle! int cycle_point = state_map[next_tree]; #if STUTTERED_VERBOSE std::cerr << "-----------------------\n"; for (unsigned int i = 0; i < state_vector.size(); i++) { std::cerr << "[" << i << "] "; if (cycle_point == i) { std::cerr << "* "; } std::cerr << "\n" << state_vector[i]->toString() << std::endl; } std::cerr << "-----------------------\n"; #endif prefix_and_cycle_state_t pac = calculate_prefix_and_cycle_state(state_vector, cycle_point); //DA_State da_prefix = null; DA_State da_cycle = null; if (pac.prefix_state != null && !(pac.prefix_state == pac.cycle_state)) { DA_State da_prefix = add_transition(da_from, pac.prefix_state, elem); da_cycle = add_transition(da_prefix, pac.cycle_state, elem); } else { da_cycle = add_transition(da_from, pac.cycle_state, elem); } da_cycle.edges().set(elem, da_cycle); return; } } }