/** * Add a new state. * @return a pointer to the newly generated state */ public NBA_State newState() { //_state_count++; NBA_State state = new NBA_State(this, _index.Count); _index.Add(state); return(state); }
/** * Calculate the set of states that are accepting and have a true self loop. */ public void calculateAcceptingTrueLoops() { _accepting_true_loops = new BitSet(); //BitSet isAcceptingTrueLoop= *_accepting_true_loops; BitSet isAcceptingTrueLoop = _accepting_true_loops;////////changed SCCs sccs = getSCCs(); for (int scc = 0; scc < sccs.countSCCs(); ++scc) { if (sccs[scc].cardinality() == 1) { int state_id = sccs[scc].nextSetBit(0); NBA_State state = _nba[state_id]; if (!state.isFinal()) { // not final, consider next continue; } if (!sccs.successors(scc).isEmpty())//////////note here { // there are edges leaving this state, consider next continue; } bool no_empty_to = true; if (sccs.stateIsReachable(state_id, state_id)) { // state has at least one self-loop // we have to check that there is no edge with empty To //for (typename NBA_t::edge_iterator eit=state->edges_begin(); eit!=state->edges_end(); ++eit) //BitSet[] edges = state._edge_manager._container._storage; //foreach (BitSet eit in edges) for (KeyValuePair <APElement, BitSet> eit = state.edges_begin(); !state.edges_end(); eit = state.increment()) { BitSet edge = eit.Value; if (edge.isEmpty()) { // not all edges lead back to the state... no_empty_to = false; break; } } if (no_empty_to) { // When we are here the state is a final true loop isAcceptingTrueLoop.set(state_id); // std::cerr << "True Loop: " << state_id << std::endl; } } } } }
public NBA(APSet apset) { //_state_count = 0; _apset = apset; _start_state = null; //ly: added to the source _index = new List <NBA_State>(); _final_states = new BitSet(); }
public NBA(APSet apset) { //_state_count = 0; _apset = apset; _start_state = null; //ly: added to the source _index = new List<NBA_State>(); _final_states = new BitSet(); }
public EdgeContainerExplicit_APElement <BitSet> _container; //<BitSet> /** * Constructor. * @param state the NBA_State owning this EdgeManager * @param apset the underlying APSet */ public NBA_State_EdgeManager(NBA_State state, APSet apset) { _state = state; _container = new EdgeContainerExplicit_APElement <BitSet>(apset.size()); //for (APSet::element_iterator eit=apset.all_elements_begin(); eit!=apset.all_elements_end(); ++eit) { for (int i = apset.all_elements_begin(); i != apset.all_elements_end(); i++) { _container.addEdge(new APElement(i), new BitSet()); } }
/** 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(); } }
/** Checks to see if NBA has only accepting (final) states. * @return true iff all states are accepting */ public bool areAllStatesFinal() { //for (typename NBA_t::iterator it=_nba.begin(); it!=_nba.end(); ++it) for (int i = 0; i < _nba._index.Count; i++) { NBA_State it = _nba[i]; if (!it.isFinal()) { return(false); } } return(true); }
/** * Checks if the NBA is deterministic (every edge has at most one target state). */ public bool isDeterministic() { //for (iterator state_it = begin(); state_it != end(); ++state_it) for (int i = 0; i < this._index.Count; i++) { NBA_State state = this._index[i]; //for (edge_iterator edge_it = state.edges_begin(); edge_it != state.edges_end(); ++edge_it) //BitSet[] edges = state._edge_manager._container._storage; //foreach (BitSet edge in edges) for (KeyValuePair <APElement, BitSet> edge = state.edges_begin(); !state.edges_end(); edge = state.increment()) { //edge_type edge = edge_it; if (edge.Value.cardinality() > 1) { return(false); } } } return(true); }
/** * Remove states from the set of accepting (final) states when this is redundant. * @param sccs the SCCs of the NBA */ public void removeRedundantFinalStates(SCCs sccs) { for (int scc = 0; scc < sccs.countSCCs(); ++scc) { if (sccs[scc].cardinality() == 1) { int state_id = sccs[scc].nextSetBit(0); NBA_State state = this[state_id]; if (state.isFinal()) { if (!sccs.stateIsReachable(state_id, state_id)) { // The state is final and has no self-loop // -> the final flag is redundant state.setFinal(false); // std::cerr << "Removing final flag for " << state_id << std::endl; } } } } }
/** Calculate the SCCs*/ public void calculate(bool disjoint) { current_dfs_nr = 0; //_dfs_data.Clear(); // Ensure there are as many entries as there are graph-states //_dfs_data.resize(_graph.size()); //Ultility.resize(_dfs_data, _graph.size()); Ultility.resizeExact(_dfs_data, _graph.size()); scc_nr = 0; NBA_State start_state = _graph.getStartState(); if (start_state == null) { return; } if (!disjoint) { int start_idx = start_state.getName(); visit(start_idx); } else { // The Graph may be disjoint -> restart DFS on every not yet visited state for (int v = 0; v < _graph.size(); ++v) { if (_dfs_data[v] == null) //.get() { // not yet visited visit(v); } } } calculateDAG(); }
/** * Add edge(s) from this state to the other state * @param monom an APMonom for the label(s) * @param to_state the target state */ public void addEdge(APMonom monom, NBA_State to_state) { _edge_manager.addEdge(monom, to_state); }
/** * 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); }
/** 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(); } }
///** 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()); }
public EdgeContainerExplicit_APElement<BitSet> _container; //<BitSet> /** * Constructor. * @param state the NBA_State owning this EdgeManager * @param apset the underlying APSet */ public NBA_State_EdgeManager(NBA_State state, APSet apset) { _state = state; _container = new EdgeContainerExplicit_APElement<BitSet>(apset.size()); //for (APSet::element_iterator eit=apset.all_elements_begin(); eit!=apset.all_elements_end(); ++eit) { for (int i = apset.all_elements_begin(); i != apset.all_elements_end(); i++) { _container.addEdge(new APElement(i), new BitSet()); } }
/** 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); }
/** Set the start state. */ public void setStartState(NBA_State state) { _start_state = state; }
/** Get the index for a state. */ public int getIndexForState(NBA_State state) { return(_index.IndexOf(state)); //.get_index }
/** Get the index for a state. */ public int getIndexForState(NBA_State state) { return _index.IndexOf(state); //.get_index }
/** Calculate the stutter closure for the NBA, for all symbols. * @param nba the NBA */ public static NBA stutter_closure(NBA nba) { 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++) { for (int j = 0; j < element_count; j++) { int st = result.nba_i_newState(); Debug.Assert(st == nba.size() + (i * element_count) + j); result[st].addEdge(new APElement(j), result[i]); result[st].addEdge(new APElement(j), result[st]); } } List <List <BitSet> > reachable = new List <List <BitSet> >(); //reachable.resize(element_count); Ultility.resize(reachable, element_count); for (int j = 0; j < element_count; j++) { //NBAEdgeSuccessors edge_successor = new NBAEdgeSuccessors(new APElement(j)); SCCs scc = new SCCs(); GraphAlgorithms.calculateSCCs(nba, scc, true, new APElement(j)); //,edge_successor reachable[j] = scc.getReachabilityForAllStates(); #if VERBOSE std::cerr << "SCCs for " << APElement(j).toString(*apset) << std::endl; std::cerr << scc << std::endl; std::cerr << " Reachability: " << std::endl; std::vector <BitSet>& reach = *reachable[j]; for (unsigned int t = 0; t < reach.size(); t++) { std::cerr << t << " -> " << reach[t] << std::endl; } std::cerr << " ---\n"; #endif } 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)); //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 * element_count) + j; 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[j][to_state]); } from.getEdge(new APElement(j)).Assign(result_to); } } //for (int i=0; i<reachable.size(); ++i) { // delete reachable[i]; // } return(nba_result_ptr); }
public static void dba2dra(NBA nba, DRA dra_result, bool complement) { //complement=false DRA dra = dra_result; APSet ap_set = dra.getAPSet();; dra.acceptance().newAcceptancePair(); for (int i = 0; i < nba.size(); i++) { dra.newState(); if (complement) { // Final states -> U_0, all states -> L_0 if (nba[i].isFinal()) { dra.acceptance().stateIn_U(0, i); } dra.acceptance().stateIn_L(0, i); } else { // Final states -> L_0, U_0 is empty if (nba[i].isFinal()) { dra.acceptance().stateIn_L(0, i); } } } if (nba.getStartState() != null) { dra.setStartState(dra[nba.getStartState().getName()]); } DA_State sink_state = null; for (int i = 0; i < nba.size(); i++) { NBA_State nba_state = nba[i]; DA_State dra_from = dra[i]; //for (APSet::element_iterator label=ap_set->all_elements_begin();label!=ap_set->all_elements_end(); ++label) for (int label = ap_set.all_elements_begin(); label != ap_set.all_elements_end(); ++label) { BitSet to = nba_state.getEdge(new APElement(label)); int to_cardinality = 0; if (to != null) { to_cardinality = to.cardinality(); } DA_State dra_to = null; if (to == null || to_cardinality == 0) { // empty to -> go to sink state if (sink_state == null) { // we have to create the sink sink_state = dra.newState(); // if we complement, we have to add the sink to // L_0 if (complement) { sink_state.acceptance().addTo_L(0); } } dra_to = sink_state; } else if (to_cardinality == 1) { int to_index = to.nextSetBit(0); // std::cerr << "to: " << to_index << std::endl; dra_to = dra[to_index]; } else { // to_cardinality>1 ! throw new IllegalArgumentException("NBA is no DBA!"); } dra_from.edges().addEdge(new APElement(label), dra_to); } } if (sink_state != null) { // there is a sink state // make true-loop from sink state to itself //for (APSet::element_iterator label=ap_set->all_elements_begin();label!=ap_set->all_elements_end();++label) { for (int label = ap_set.all_elements_begin(); label != ap_set.all_elements_end(); ++label) { sink_state.edges().addEdge(new APElement(label), sink_state); } } }
/** * Add a new state. * @return a pointer to the newly generated state */ public NBA_State newState() { //_state_count++; NBA_State state = new NBA_State(this, _index.Count); _index.Add(state); return state; }