diff --git a/alib2algo/src/determinize/vpa/VPADeterminizer.cpp b/alib2algo/src/determinize/vpa/VPADeterminizer.cpp index a676e490c9360884e5fae68261c75cf878e68d20..d820e5197d5ba153dcc15163863d27551bcca20a 100644 --- a/alib2algo/src/determinize/vpa/VPADeterminizer.cpp +++ b/alib2algo/src/determinize/vpa/VPADeterminizer.cpp @@ -6,6 +6,7 @@ #include "label/Label.h" #include "label/LabelSetLabel.h" #include "label/LabelPairLabel.h" +#include <std/set.hpp> namespace determinize { @@ -291,7 +292,7 @@ automaton::VisiblyPushdownNPDA VPADeterminizer::determinize(const automaton::Vis std::pair<label::Label, alphabet::Symbol>* stateSymbol = existsDirtyStateSymbol(d); const automaton::State* state = existsDirtyState(d); if(stateSymbol != NULL) { - for(alphabet::Symbol symbol : n.getReturnInputAlphabet()) { + for(const alphabet::Symbol& symbol : n.getReturnInputAlphabet()) { if(stateSymbol->second == d.getBottomOfTheStackSymbol()) { retInitial(stateSymbol->first, stateSymbol->second, symbol, n, d); } else { @@ -300,26 +301,22 @@ automaton::VisiblyPushdownNPDA VPADeterminizer::determinize(const automaton::Vis } delete stateSymbol; //TODO remove this... } else if(state != NULL) { - for(alphabet::Symbol symbol : n.getLocalInputAlphabet()) { + for(const alphabet::Symbol& symbol : n.getLocalInputAlphabet()) { local(*state, symbol, n, d); } - for(alphabet::Symbol symbol : n.getCallInputAlphabet()) { + for(const alphabet::Symbol symbol : n.getCallInputAlphabet()) { call(*state, symbol, n, d); } } else { break; } } - - std::set<label::Label> fin = retrieveLabels(n.getFinalStates()); - - for(automaton::State state : d.getStates()) { - std::set<label::Label> labels = retrieveDSubSet(VPADeterminizer::unpackFromDVPAStateLabel(state.getName())); - std::set<label::Label> finalLabels(fin); - finalLabels.erase(labels.begin(), labels.end()); - - if(!finalLabels.empty()) { + std::set<label::Label> finalLabels = retrieveLabels(n.getFinalStates()); + for(const automaton::State& state : d.getStates()) { + const std::set<label::Label> labels = retrieveDSubSet(VPADeterminizer::unpackFromDVPAStateLabel(state.getName())); + + if(!std::empty_intersection(finalLabels, labels)) { d.addFinalState(state); } } diff --git a/alib2algo/test-src/determinize/determinizeTest.cpp b/alib2algo/test-src/determinize/determinizeTest.cpp index 6f7187a5602c21a0813b7a0ddcb2f6d03b4be6aa..e19b33138d46646285795f37cf1c905d7be10fee 100644 --- a/alib2algo/test-src/determinize/determinizeTest.cpp +++ b/alib2algo/test-src/determinize/determinizeTest.cpp @@ -67,3 +67,49 @@ void determinizeTest::testDeterminizeIDPDA() { CPPUNIT_ASSERT(determinized.getStates().size() == 3); } + +void determinizeTest::testDeterminizeVPA() { + automaton::VisiblyPushdownNPDA automaton(alphabet::Symbol(alphabet::BottomOfTheStackSymbol {})); + + automaton.addCallInputSymbol(alphabet::symbolFrom('a')); + automaton.addReturnInputSymbol(alphabet::symbolFrom('^')); + + automaton.addStackSymbol(alphabet::symbolFrom('A')); + automaton.addStackSymbol(alphabet::symbolFrom('B')); + automaton.addStackSymbol(alphabet::symbolFrom('C')); + automaton.addStackSymbol(alphabet::symbolFrom('D')); + automaton.addStackSymbol(alphabet::symbolFrom('E')); + automaton.addStackSymbol(alphabet::symbolFrom('F')); + automaton.addStackSymbol(alphabet::symbolFrom('T')); + + automaton.addState(automaton::State(0)); + automaton.addState(automaton::State(1)); + automaton.addState(automaton::State(2)); + automaton.addState(automaton::State(3)); + automaton.addState(automaton::State(4)); + automaton.addState(automaton::State(5)); + automaton.addState(automaton::State(6)); + + + automaton.addTransition(automaton::State(0), alphabet::symbolFrom('a'), automaton::State(0), alphabet::symbolFrom('A')); + automaton.addTransition(automaton::State(0), alphabet::symbolFrom('^'), alphabet::symbolFrom('A'), automaton::State(0)); + + automaton.addTransition(automaton::State(0), alphabet::symbolFrom('a'), automaton::State(1), alphabet::symbolFrom('B')); + + automaton.addTransition(automaton::State(1), alphabet::symbolFrom('a'), automaton::State(2), alphabet::symbolFrom('C')); + automaton.addTransition(automaton::State(2), alphabet::symbolFrom('a'), automaton::State(2), alphabet::symbolFrom('D')); + automaton.addTransition(automaton::State(2), alphabet::symbolFrom('^'), alphabet::symbolFrom('D'), automaton::State(2)); + automaton.addTransition(automaton::State(2), alphabet::symbolFrom('^'), alphabet::symbolFrom('C'), automaton::State(3)); + + automaton.addTransition(automaton::State(3), alphabet::symbolFrom('a'), automaton::State(4), alphabet::symbolFrom('E')); + automaton.addTransition(automaton::State(4), alphabet::symbolFrom('a'), automaton::State(4), alphabet::symbolFrom('F')); + automaton.addTransition(automaton::State(4), alphabet::symbolFrom('^'), alphabet::symbolFrom('F'), automaton::State(4)); + automaton.addTransition(automaton::State(4), alphabet::symbolFrom('^'), alphabet::symbolFrom('E'), automaton::State(5)); + + automaton.addTransition(automaton::State(5), alphabet::symbolFrom('^'), alphabet::symbolFrom('B'), automaton::State(6)); + + automaton.addInitialState(automaton::State(0)); + automaton.addFinalState(automaton::State(4)); + + alib::DataFactory::toStdout(automaton); +} diff --git a/alib2algo/test-src/determinize/determinizeTest.h b/alib2algo/test-src/determinize/determinizeTest.h index 0d2d93e80ba74618c53f7df18bb6465649c6b962..1269f9ad95c40d94cadf1129ca8ab0b62d1de74e 100644 --- a/alib2algo/test-src/determinize/determinizeTest.h +++ b/alib2algo/test-src/determinize/determinizeTest.h @@ -8,6 +8,7 @@ class determinizeTest : public CppUnit::TestFixture CPPUNIT_TEST_SUITE( determinizeTest ); CPPUNIT_TEST( testDeterminizeNFA ); CPPUNIT_TEST( testDeterminizeIDPDA ); + CPPUNIT_TEST( testDeterminizeVPA ); CPPUNIT_TEST_SUITE_END(); public: @@ -16,6 +17,7 @@ public: void testDeterminizeNFA(); void testDeterminizeIDPDA(); + void testDeterminizeVPA(); }; #endif // DETERMINIZE_TEST_H_