From 496852b9885640b44b46bb63c7b09c3fb4df13b3 Mon Sep 17 00:00:00 2001 From: Tomas Pecka <peckato1@fit.cvut.cz> Date: Sun, 24 Feb 2019 13:10:13 +0100 Subject: [PATCH] Unit tests: CPPUNIT -> Catch2: algo --- .../automaton/convert/FTAtoPDATest.cpp | 130 +++--- .../test-src/automaton/convert/FTAtoPDATest.h | 21 - .../automaton/determinize/determinizeTest.cpp | 192 ++++----- .../automaton/determinize/determinizeTest.h | 25 -- .../properties/EpsilonClosureTest.cpp | 69 ++- .../automaton/properties/EpsilonClosureTest.h | 19 - .../simplify/FSMSingleInitialStateTest.cpp | 83 ++-- .../simplify/FSMSingleInitialStateTest.h | 19 - .../automaton/simplify/FSMTotalTest.cpp | 57 ++- .../automaton/simplify/FSMTotalTest.h | 19 - .../simplify/minimizeBrzozowskiTest.cpp | 46 +- .../simplify/minimizeBrzozowskiTest.h | 19 - .../automaton/simplify/minimizeTest.cpp | 302 +++++++------ .../automaton/simplify/minimizeTest.h | 20 - .../automaton/simplify/normalizeTest.cpp | 61 ++- .../automaton/simplify/normalizeTest.h | 19 - .../test-src/automaton/simplify/trimTest.cpp | 167 +++----- .../test-src/automaton/simplify/trimTest.h | 22 - .../transform/AutomataCompactionTest.cpp | 223 +++++----- .../transform/AutomataCompactionTest.h | 23 - .../transform/AutomataConcatenationTest.cpp | 129 +++--- .../transform/AutomataConcatenationTest.h | 19 - .../automaton/transform/AutomataUnionTest.cpp | 25 +- .../automaton/transform/AutomataUnionTest.h | 19 - .../transform/AutomatonIterationTest.cpp | 95 ++--- .../transform/AutomatonIterationTest.h | 19 - .../grammar/convert/GrammarCFGtoPDATest.cpp | 25 +- .../grammar/convert/GrammarCFGtoPDATest.h | 21 - .../test-src/grammar/convert/rg2rgTest.cpp | 69 +++ .../generate/GrammarGenerateUpToLength.cpp | 354 ++++++++-------- .../generate/GrammarGenerateUpToLength.h | 23 - .../properties/GrammarPropertiesTest.cpp | 258 ++++++------ .../properties/GrammarPropertiesTest.h | 23 - .../simplify/GrammarEpsilonRemoverTest.cpp | 247 ++++++----- .../simplify/GrammarEpsilonRemoverTest.h | 23 - .../GrammarLeftRecursionRemoverTest.cpp | 383 ++++++++--------- .../GrammarLeftRecursionRemoverTest.h | 27 -- .../GrammarSimpleRulesRemoverTest.cpp | 239 +++++------ .../simplify/GrammarSimpleRulesRemoverTest.h | 23 - .../grammar/simplify/GrammarToCNFTest.cpp | 172 ++++---- .../grammar/simplify/GrammarToCNFTest.h | 21 - .../grammar/simplify/GrammarToGNFTest.cpp | 307 +++++++------- .../grammar/simplify/GrammarToGNFTest.h | 25 -- .../test-src/grammar/simplify/TrimTest.cpp | 34 ++ .../test-src/grammar/toGrammar/rg2rgTest.cpp | 78 ---- .../test-src/grammar/toGrammar/rg2rgTest.h | 21 - alib2algo/test-src/main.cpp | 168 +------- alib2algo/test-src/playTest.cpp | 89 ---- alib2algo/test-src/playTest.h | 30 -- alib2algo/test-src/regexp/RegExpTest.cpp | 124 ------ alib2algo/test-src/regexp/RegExpTest.h | 23 - .../regexp/convert/ToAutomatonTest.cpp | 81 ++++ .../test-src/regexp/glushkov/GlushkovTest.cpp | 117 ++++++ .../regexp/properties/RegExpEmptyTest.cpp | 32 -- .../regexp/properties/RegExpEmptyTest.h | 21 - .../regexp/properties/RegExpEpsilonTest.cpp | 60 --- .../regexp/properties/RegExpEpsilonTest.h | 21 - .../properties/RegExpPropertiesTest.cpp | 69 +++ .../regexp/simplify/RegExpOptimizeTest.cpp | 397 ++++++------------ .../regexp/simplify/RegExpOptimizeTest.h | 21 - .../test-src/regexp/toAutomaton/re2faTest.cpp | 93 ---- .../test-src/regexp/toAutomaton/re2faTest.h | 23 - .../transform/RegExpConcatenateTest.cpp | 66 +-- .../regexp/transform/RegExpConcatenateTest.h | 21 - .../regexp/transform/RegExpDerivationTest.cpp | 56 ++- .../regexp/transform/RegExpDerivationTest.h | 23 - .../regexp/transform/RegExpIntegralTest.cpp | 34 +- .../regexp/transform/RegExpIntegralTest.h | 23 - .../test-src/string/compare/compareTest.cpp | 92 ++-- .../test-src/string/compare/compareTest.h | 23 - .../string/properties/borderArrayTest.cpp | 23 +- .../string/properties/borderArrayTest.h | 19 - .../compression/ArithmeticCompressionTest.cpp | 31 +- .../compression/ArithmeticCompressionTest.h | 19 - .../stringology/compression/LZ77Test.cpp | 118 ++---- .../stringology/compression/LZ77Test.h | 27 -- .../stringology/exact/stringMatchTest.cpp | 23 +- .../stringology/exact/stringMatchTest.h | 19 - .../indexing/ExactSuffixAutomatonTest.cpp | 62 ++- .../indexing/ExactSuffixAutomatonTest.h | 19 - .../indexing/FactorOracleAutomatonTest.cpp | 59 ++- .../indexing/FactorOracleAutomatonTest.h | 18 - ...ckwardNondeterministicDAWGMatchingTest.cpp | 78 ++-- ...BackwardNondeterministicDAWGMatchingTest.h | 18 - ...alizedLevenshteinMatchingAutomatonTest.cpp | 266 ++++++------ ...eralizedLevenshteinMatchingAutomatonTest.h | 19 - ...venshteinSequenceMatchingAutomatonTest.cpp | 332 +++++++-------- ...LevenshteinSequenceMatchingAutomatonTest.h | 19 - .../matching/HammingMatchingAutomatonTest.cpp | 165 ++++---- .../matching/HammingMatchingAutomatonTest.h | 19 - .../HammingSequenceMatchingAutomatonTest.cpp | 204 +++++---- .../HammingSequenceMatchingAutomatonTest.h | 19 - .../LevenshteinMatchingAutomatonTest.cpp | 226 +++++----- .../LevenshteinMatchingAutomatonTest.h | 19 - ...venshteinSequenceMatchingAutomatonTest.cpp | 259 ++++++------ ...LevenshteinSequenceMatchingAutomatonTest.h | 19 - .../SequenceMatchingAutomatonTest.cpp | 58 ++- .../matching/SequenceMatchingAutomatonTest.h | 17 - .../stringology/query/DAWGMatcherTest.cpp | 80 ++-- .../stringology/query/DAWGMatcherTest.h | 19 - .../stringology/query/OracleMatcherTest.cpp | 77 ++-- .../stringology/query/OracleMatcherTest.h | 19 - .../simulations/ExactBitParalelismTest.cpp | 21 +- .../simulations/ExactBitParalelismTest.h | 17 - ...eneralizedLevenshteinBitParalelismTest.cpp | 23 +- .../GeneralizedLevenshteinBitParalelismTest.h | 17 - ...lizedLevenshteinDynamicProgrammingTest.cpp | 61 ++- ...ralizedLevenshteinDynamicProgrammingTest.h | 19 - .../simulations/HammingBitParalelismTest.cpp | 23 +- .../simulations/HammingBitParalelismTest.h | 17 - .../HammingDynamicProgrammingTest.cpp | 62 ++- .../HammingDynamicProgrammingTest.h | 19 - .../LevenshteinBitParalelismTest.cpp | 23 +- .../LevenshteinBitParalelismTest.h | 17 - .../LevenshteinDynamicProgrammingTest.cpp | 60 ++- .../LevenshteinDynamicProgrammingTest.h | 19 - 116 files changed, 3338 insertions(+), 5351 deletions(-) delete mode 100644 alib2algo/test-src/automaton/convert/FTAtoPDATest.h delete mode 100644 alib2algo/test-src/automaton/determinize/determinizeTest.h delete mode 100644 alib2algo/test-src/automaton/properties/EpsilonClosureTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/FSMTotalTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/minimizeTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/normalizeTest.h delete mode 100644 alib2algo/test-src/automaton/simplify/trimTest.h delete mode 100644 alib2algo/test-src/automaton/transform/AutomataCompactionTest.h delete mode 100644 alib2algo/test-src/automaton/transform/AutomataConcatenationTest.h delete mode 100644 alib2algo/test-src/automaton/transform/AutomataUnionTest.h delete mode 100644 alib2algo/test-src/automaton/transform/AutomatonIterationTest.h delete mode 100644 alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.h create mode 100644 alib2algo/test-src/grammar/convert/rg2rgTest.cpp delete mode 100644 alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.h delete mode 100644 alib2algo/test-src/grammar/properties/GrammarPropertiesTest.h delete mode 100644 alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.h delete mode 100644 alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.h delete mode 100644 alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.h delete mode 100644 alib2algo/test-src/grammar/simplify/GrammarToCNFTest.h delete mode 100644 alib2algo/test-src/grammar/simplify/GrammarToGNFTest.h create mode 100644 alib2algo/test-src/grammar/simplify/TrimTest.cpp delete mode 100644 alib2algo/test-src/grammar/toGrammar/rg2rgTest.cpp delete mode 100644 alib2algo/test-src/grammar/toGrammar/rg2rgTest.h delete mode 100644 alib2algo/test-src/playTest.cpp delete mode 100644 alib2algo/test-src/playTest.h delete mode 100644 alib2algo/test-src/regexp/RegExpTest.cpp delete mode 100644 alib2algo/test-src/regexp/RegExpTest.h create mode 100644 alib2algo/test-src/regexp/convert/ToAutomatonTest.cpp create mode 100644 alib2algo/test-src/regexp/glushkov/GlushkovTest.cpp delete mode 100644 alib2algo/test-src/regexp/properties/RegExpEmptyTest.cpp delete mode 100644 alib2algo/test-src/regexp/properties/RegExpEmptyTest.h delete mode 100644 alib2algo/test-src/regexp/properties/RegExpEpsilonTest.cpp delete mode 100644 alib2algo/test-src/regexp/properties/RegExpEpsilonTest.h create mode 100644 alib2algo/test-src/regexp/properties/RegExpPropertiesTest.cpp delete mode 100644 alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.h delete mode 100644 alib2algo/test-src/regexp/toAutomaton/re2faTest.cpp delete mode 100644 alib2algo/test-src/regexp/toAutomaton/re2faTest.h delete mode 100644 alib2algo/test-src/regexp/transform/RegExpConcatenateTest.h delete mode 100644 alib2algo/test-src/regexp/transform/RegExpDerivationTest.h delete mode 100644 alib2algo/test-src/regexp/transform/RegExpIntegralTest.h delete mode 100644 alib2algo/test-src/string/compare/compareTest.h delete mode 100644 alib2algo/test-src/string/properties/borderArrayTest.h delete mode 100644 alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.h delete mode 100644 alib2algo/test-src/stringology/compression/LZ77Test.h delete mode 100644 alib2algo/test-src/stringology/exact/stringMatchTest.h delete mode 100644 alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.h delete mode 100644 alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.h delete mode 100644 alib2algo/test-src/stringology/query/DAWGMatcherTest.h delete mode 100644 alib2algo/test-src/stringology/query/OracleMatcherTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.h delete mode 100644 alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.h diff --git a/alib2algo/test-src/automaton/convert/FTAtoPDATest.cpp b/alib2algo/test-src/automaton/convert/FTAtoPDATest.cpp index a576e80e52..5e8ca0332f 100644 --- a/alib2algo/test-src/automaton/convert/FTAtoPDATest.cpp +++ b/alib2algo/test-src/automaton/convert/FTAtoPDATest.cpp @@ -1,4 +1,4 @@ -#include "FTAtoPDATest.h" +#include <catch2/catch.hpp> #include <alphabet/BottomOfTheStackSymbol.h> #include <automaton/TA/DFTA.h> @@ -9,75 +9,73 @@ #include <automaton/PDA/NPDA.h> #include <automaton/xml/PDA/NPDA.h> -#include "automaton/convert/ToPostfixPushdownAutomaton.h" +#include <automaton/convert/ToPostfixPushdownAutomaton.h> #include <factory/XmlDataFactory.hpp> #include <label/InitialStateLabel.h> #include <label/FinalStateLabel.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( FTAtoPDATest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( FTAtoPDATest ); - -void FTAtoPDATest::setUp() { -} - -void FTAtoPDATest::tearDown() { -} - -void FTAtoPDATest::testDFTAtoDPDA() { - automaton::DFTA < > automaton; - - const common::ranked_symbol < > a (DefaultSymbolType('a'), DefaultRankType(2)); - const common::ranked_symbol < > b (DefaultSymbolType('b'), DefaultRankType(1)); - const common::ranked_symbol < > c (DefaultSymbolType('c'), DefaultRankType(0)); - const ext::set<common::ranked_symbol < > > alphabet {a, b, c}; - automaton.setInputAlphabet(alphabet); - - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - - ext::vector<DefaultStateType> a1States = {DefaultStateType(1), DefaultStateType(3)}; - automaton.addTransition(a, a1States, DefaultStateType(1)); - ext::vector<DefaultStateType> a2States = {DefaultStateType(3), DefaultStateType(3)}; - automaton.addTransition(a, a2States, DefaultStateType(2)); - ext::vector<DefaultStateType> bStates = {DefaultStateType(2)}; - automaton.addTransition(b, bStates, DefaultStateType(1)); - ext::vector<DefaultStateType> cStates; - automaton.addTransition(c, cStates, DefaultStateType(3)); - - automaton.addFinalState(DefaultStateType(3)); - - automaton::DPDA < > res = automaton::convert::ToPostfixPushdownAutomaton::convert(automaton); - factory::XmlDataFactory::toStdout(res); -} - -void FTAtoPDATest::testNFTAtoNPDA() { - automaton::NFTA < > automaton; - - const common::ranked_symbol < > a (DefaultSymbolType('a'), DefaultRankType(2)); - const common::ranked_symbol < > b (DefaultSymbolType('b'), DefaultRankType(1)); - const common::ranked_symbol < > c (DefaultSymbolType('c'), DefaultRankType(0)); - const ext::set<common::ranked_symbol < > > alphabet {a, b, c}; - automaton.setInputAlphabet(alphabet); - - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - - ext::vector<DefaultStateType> a1States = {DefaultStateType(1), DefaultStateType(3)}; - automaton.addTransition(a, a1States, DefaultStateType(1)); - automaton.addTransition(a, a1States, DefaultStateType(3)); - ext::vector<DefaultStateType> a2States = {DefaultStateType(3), DefaultStateType(3)}; - automaton.addTransition(a, a2States, DefaultStateType(2)); - ext::vector<DefaultStateType> bStates = {DefaultStateType(2)}; - automaton.addTransition(b, bStates, DefaultStateType(1)); - ext::vector<DefaultStateType> cStates; - automaton.addTransition(c, cStates, DefaultStateType(3)); - - automaton.addFinalState(DefaultStateType(3)); - - automaton::NPDA < > res = automaton::convert::ToPostfixPushdownAutomaton::convert(automaton); - factory::XmlDataFactory::toStdout(res); +TEST_CASE ( "FTAtoPDA", "[unit][algo][automaton][convert]" ) { + SECTION ( "Test DFTA to DPDA" ) { + automaton::DFTA < > automaton; + + const common::ranked_symbol < > a (DefaultSymbolType('a'), DefaultRankType(2)); + const common::ranked_symbol < > b (DefaultSymbolType('b'), DefaultRankType(1)); + const common::ranked_symbol < > c (DefaultSymbolType('c'), DefaultRankType(0)); + const ext::set<common::ranked_symbol < > > alphabet {a, b, c}; + automaton.setInputAlphabet(alphabet); + + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + + ext::vector<DefaultStateType> a1States = {DefaultStateType(1), DefaultStateType(3)}; + automaton.addTransition(a, a1States, DefaultStateType(1)); + ext::vector<DefaultStateType> a2States = {DefaultStateType(3), DefaultStateType(3)}; + automaton.addTransition(a, a2States, DefaultStateType(2)); + ext::vector<DefaultStateType> bStates = {DefaultStateType(2)}; + automaton.addTransition(b, bStates, DefaultStateType(1)); + ext::vector<DefaultStateType> cStates; + automaton.addTransition(c, cStates, DefaultStateType(3)); + + automaton.addFinalState(DefaultStateType(3)); + + automaton::DPDA < > res = automaton::convert::ToPostfixPushdownAutomaton::convert(automaton); + CHECK(res.getStates().size() == 2); + CHECK(res.getTransitions().size() == 5); + CHECK(res.getFinalStates().size() == 1); + } + + SECTION ( "Test NFTA to NPDA" ) { + automaton::NFTA < > automaton; + + const common::ranked_symbol < > a (DefaultSymbolType('a'), DefaultRankType(2)); + const common::ranked_symbol < > b (DefaultSymbolType('b'), DefaultRankType(1)); + const common::ranked_symbol < > c (DefaultSymbolType('c'), DefaultRankType(0)); + const ext::set<common::ranked_symbol < > > alphabet {a, b, c}; + automaton.setInputAlphabet(alphabet); + + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + + ext::vector<DefaultStateType> a1States = {DefaultStateType(1), DefaultStateType(3)}; + automaton.addTransition(a, a1States, DefaultStateType(1)); + automaton.addTransition(a, a1States, DefaultStateType(3)); + ext::vector<DefaultStateType> a2States = {DefaultStateType(3), DefaultStateType(3)}; + automaton.addTransition(a, a2States, DefaultStateType(2)); + ext::vector<DefaultStateType> bStates = {DefaultStateType(2)}; + automaton.addTransition(b, bStates, DefaultStateType(1)); + ext::vector<DefaultStateType> cStates; + automaton.addTransition(c, cStates, DefaultStateType(3)); + + automaton.addFinalState(DefaultStateType(3)); + + automaton::NPDA < > res = automaton::convert::ToPostfixPushdownAutomaton::convert(automaton); + + CHECK(res.getStates().size() == 2); + CHECK(res.getTransitions().size() == 5); + CHECK(res.getFinalStates().size() == 1); + } } diff --git a/alib2algo/test-src/automaton/convert/FTAtoPDATest.h b/alib2algo/test-src/automaton/convert/FTAtoPDATest.h deleted file mode 100644 index 8a09fd668c..0000000000 --- a/alib2algo/test-src/automaton/convert/FTAtoPDATest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef FTA_TO_PDA_TEST_H_ -#define FTA_TO_PDA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class FTAtoPDATest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( FTAtoPDATest ); - CPPUNIT_TEST( testDFTAtoDPDA ); - CPPUNIT_TEST( testNFTAtoNPDA ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testDFTAtoDPDA(); - void testNFTAtoNPDA(); -}; - -#endif /* FTA_TO_PDA_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/determinize/determinizeTest.cpp b/alib2algo/test-src/automaton/determinize/determinizeTest.cpp index 169f695eec..5ce25695d9 100644 --- a/alib2algo/test-src/automaton/determinize/determinizeTest.cpp +++ b/alib2algo/test-src/automaton/determinize/determinizeTest.cpp @@ -1,139 +1,141 @@ +#include <catch2/catch.hpp> #include <alib/list> -#include "determinizeTest.h" #include <automaton/FSM/NFA.h> #include <automaton/TA/NFTA.h> #include <automaton/PDA/InputDrivenNPDA.h> #include <automaton/PDA/InputDrivenDPDA.h> #include <automaton/PDA/VisiblyPushdownNPDA.h> +#include <automaton/PDA/VisiblyPushdownDPDA.h> #include <alphabet/BottomOfTheStackSymbol.h> -#include "automaton/determinize/Determinize.h" +#include <automaton/determinize/Determinize.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( determinizeTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( determinizeTest ); +TEST_CASE ( "Determinize", "[unit][algo][automaton][determinize]" ) { + SECTION ( "NFA" ) { + automaton::NFA < > automaton(DefaultStateType(1)); -void determinizeTest::setUp() { -} + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); -void determinizeTest::tearDown() { -} + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); + automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); -void determinizeTest::testDeterminizeNFA() { - automaton::NFA < > automaton(DefaultStateType(1)); + automaton.addFinalState(DefaultStateType(3)); - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); + automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > determinized = automaton::determinize::Determinize::determinize(automaton); - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); - automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); + CHECK(determinized.getStates().size() == 3); - automaton.addFinalState(DefaultStateType(3)); + } - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > determinized = automaton::determinize::Determinize::determinize(automaton); + SECTION ( "IDPDA" ) { + automaton::InputDrivenNPDA < > automaton(DefaultStateType(1), DefaultSymbolType('S')); - CPPUNIT_ASSERT(determinized.getStates().size() == 3); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); -} + automaton.setPushdownStoreOperation(DefaultSymbolType("a"), ext::vector<DefaultSymbolType>{}, ext::vector<DefaultSymbolType> {}); + automaton.setPushdownStoreOperation(DefaultSymbolType("b"), ext::vector<DefaultSymbolType>{}, ext::vector<DefaultSymbolType> {}); -void determinizeTest::testDeterminizeIDPDA() { - automaton::InputDrivenNPDA < > automaton(DefaultStateType(1), DefaultSymbolType('S')); + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); + automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); + automaton.addFinalState(DefaultStateType(3)); - automaton.setPushdownStoreOperation(DefaultSymbolType("a"), ext::vector<DefaultSymbolType>{}, ext::vector<DefaultSymbolType> {}); - automaton.setPushdownStoreOperation(DefaultSymbolType("b"), ext::vector<DefaultSymbolType>{}, ext::vector<DefaultSymbolType> {}); + automaton::InputDrivenDPDA < DefaultSymbolType, DefaultSymbolType, ext::set < DefaultStateType > > determinized = automaton::determinize::Determinize::determinize(automaton); - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); - automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); + CHECK(determinized.getStates().size() == 3); + } - automaton.addFinalState(DefaultStateType(3)); + SECTION ( "VPA" ) { + automaton::VisiblyPushdownNPDA < > automaton(DefaultSymbolType(alphabet::BottomOfTheStackSymbol {})); - automaton::InputDrivenDPDA < DefaultSymbolType, DefaultSymbolType, ext::set < DefaultStateType > > determinized = automaton::determinize::Determinize::determinize(automaton); + automaton.addCallInputSymbol(DefaultSymbolType('a')); + automaton.addReturnInputSymbol(DefaultSymbolType('^')); - CPPUNIT_ASSERT(determinized.getStates().size() == 3); -} + automaton.addPushdownStoreSymbol(DefaultSymbolType('A')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('B')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('C')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('D')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('E')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('F')); + automaton.addPushdownStoreSymbol(DefaultSymbolType('T')); -void determinizeTest::testDeterminizeVPA() { - automaton::VisiblyPushdownNPDA < > automaton(DefaultSymbolType(alphabet::BottomOfTheStackSymbol {})); + automaton.addState(DefaultStateType(0)); + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addState(DefaultStateType(4)); + automaton.addState(DefaultStateType(5)); + automaton.addState(DefaultStateType(6)); - automaton.addCallInputSymbol(DefaultSymbolType('a')); - automaton.addReturnInputSymbol(DefaultSymbolType('^')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('A')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('B')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('C')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('D')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('E')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('F')); - automaton.addPushdownStoreSymbol(DefaultSymbolType('T')); + automaton.addCallTransition(DefaultStateType(0), DefaultSymbolType('a'), DefaultStateType(0), DefaultSymbolType('A')); + automaton.addReturnTransition(DefaultStateType(0), DefaultSymbolType('^'), DefaultSymbolType('A'), DefaultStateType(0)); - automaton.addState(DefaultStateType(0)); - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addState(DefaultStateType(4)); - automaton.addState(DefaultStateType(5)); - automaton.addState(DefaultStateType(6)); + automaton.addCallTransition(DefaultStateType(0), DefaultSymbolType('a'), DefaultStateType(1), DefaultSymbolType('B')); + automaton.addCallTransition(DefaultStateType(1), DefaultSymbolType('a'), DefaultStateType(2), DefaultSymbolType('C')); + automaton.addCallTransition(DefaultStateType(2), DefaultSymbolType('a'), DefaultStateType(2), DefaultSymbolType('D')); + automaton.addReturnTransition(DefaultStateType(2), DefaultSymbolType('^'), DefaultSymbolType('D'), DefaultStateType(2)); + automaton.addReturnTransition(DefaultStateType(2), DefaultSymbolType('^'), DefaultSymbolType('C'), DefaultStateType(3)); - automaton.addCallTransition(DefaultStateType(0), DefaultSymbolType('a'), DefaultStateType(0), DefaultSymbolType('A')); - automaton.addReturnTransition(DefaultStateType(0), DefaultSymbolType('^'), DefaultSymbolType('A'), DefaultStateType(0)); + automaton.addCallTransition(DefaultStateType(3), DefaultSymbolType('a'), DefaultStateType(4), DefaultSymbolType('E')); + automaton.addCallTransition(DefaultStateType(4), DefaultSymbolType('a'), DefaultStateType(4), DefaultSymbolType('F')); + automaton.addReturnTransition(DefaultStateType(4), DefaultSymbolType('^'), DefaultSymbolType('F'), DefaultStateType(4)); + automaton.addReturnTransition(DefaultStateType(4), DefaultSymbolType('^'), DefaultSymbolType('E'), DefaultStateType(5)); - automaton.addCallTransition(DefaultStateType(0), DefaultSymbolType('a'), DefaultStateType(1), DefaultSymbolType('B')); + automaton.addReturnTransition(DefaultStateType(5), DefaultSymbolType('^'), DefaultSymbolType('B'), DefaultStateType(6)); - automaton.addCallTransition(DefaultStateType(1), DefaultSymbolType('a'), DefaultStateType(2), DefaultSymbolType('C')); - automaton.addCallTransition(DefaultStateType(2), DefaultSymbolType('a'), DefaultStateType(2), DefaultSymbolType('D')); - automaton.addReturnTransition(DefaultStateType(2), DefaultSymbolType('^'), DefaultSymbolType('D'), DefaultStateType(2)); - automaton.addReturnTransition(DefaultStateType(2), DefaultSymbolType('^'), DefaultSymbolType('C'), DefaultStateType(3)); + automaton.addInitialState(DefaultStateType(0)); + automaton.addFinalState(DefaultStateType(4)); - automaton.addCallTransition(DefaultStateType(3), DefaultSymbolType('a'), DefaultStateType(4), DefaultSymbolType('E')); - automaton.addCallTransition(DefaultStateType(4), DefaultSymbolType('a'), DefaultStateType(4), DefaultSymbolType('F')); - automaton.addReturnTransition(DefaultStateType(4), DefaultSymbolType('^'), DefaultSymbolType('F'), DefaultStateType(4)); - automaton.addReturnTransition(DefaultStateType(4), DefaultSymbolType('^'), DefaultSymbolType('E'), DefaultStateType(5)); - - automaton.addReturnTransition(DefaultStateType(5), DefaultSymbolType('^'), DefaultSymbolType('B'), DefaultStateType(6)); - - automaton.addInitialState(DefaultStateType(0)); - automaton.addFinalState(DefaultStateType(4)); -} + auto determinized = automaton::determinize::Determinize::determinize ( automaton ); + CHECK ( determinized.getStates().size() == 29 ); + CHECK ( determinized.getFinalStates().size() == 14 ); + CHECK ( determinized.getCallTransitions().size() == 28 ); + CHECK ( determinized.getReturnTransitions().size() == 198 ); + CHECK ( determinized.getLocalTransitions().size() == 0 ); + CHECK ( determinized.getCallTransitions().size() == 28 ); -void determinizeTest::testDeterminizeNFTA() { - automaton::NFTA < char, unsigned, int> automaton; + } - const common::ranked_symbol < char, unsigned > a ('a', 2); - const common::ranked_symbol < char, unsigned > b ('b', 1); - const common::ranked_symbol < char, unsigned > c ('c', 0); - const ext::set<common::ranked_symbol < char, unsigned > > alphabet {a, b, c}; - automaton.setInputAlphabet(alphabet); + SECTION ( "NFTA" ) { + automaton::NFTA < char, unsigned, int> automaton; - automaton.addState(1); - automaton.addState(2); - automaton.addState(3); + const common::ranked_symbol < char, unsigned > a ('a', 2); + const common::ranked_symbol < char, unsigned > b ('b', 1); + const common::ranked_symbol < char, unsigned > c ('c', 0); + const ext::set<common::ranked_symbol < char, unsigned > > alphabet {a, b, c}; + automaton.setInputAlphabet(alphabet); - ext::vector<int> a1States = {1, 3}; - automaton.addTransition(a, a1States, 1); - automaton.addTransition(a, a1States, 3); - ext::vector<int> a2States = {3, 3}; - automaton.addTransition(a, a2States, 2); - ext::vector<int> bStates = {2}; - automaton.addTransition(b, bStates, 1); - ext::vector<int> cStates; - automaton.addTransition(c, cStates, 3); + automaton.addState(1); + automaton.addState(2); + automaton.addState(3); - automaton.addFinalState(3); + ext::vector<int> a1States = {1, 3}; + automaton.addTransition(a, a1States, 1); + automaton.addTransition(a, a1States, 3); + ext::vector<int> a2States = {3, 3}; + automaton.addTransition(a, a2States, 2); + ext::vector<int> bStates = {2}; + automaton.addTransition(b, bStates, 1); + ext::vector<int> cStates; + automaton.addTransition(c, cStates, 3); + automaton.addFinalState(3); - automaton::DFTA < char, unsigned, ext::set < int > > determinized = automaton::determinize::Determinize::determinize(automaton); + automaton::DFTA < char, unsigned, ext::set < int > > determinized = automaton::determinize::Determinize::determinize(automaton); - CPPUNIT_ASSERT(determinized.getStates().size() == 5); - CPPUNIT_ASSERT(determinized.getFinalStates().size() == 3); - CPPUNIT_ASSERT(determinized.getTransitions().size() == 15); + CHECK(determinized.getStates().size() == 5); + CHECK(determinized.getFinalStates().size() == 3); + CHECK(determinized.getTransitions().size() == 15); + } } diff --git a/alib2algo/test-src/automaton/determinize/determinizeTest.h b/alib2algo/test-src/automaton/determinize/determinizeTest.h deleted file mode 100644 index 8bb94b7742..0000000000 --- a/alib2algo/test-src/automaton/determinize/determinizeTest.h +++ /dev/null @@ -1,25 +0,0 @@ -#ifndef DETERMINIZE_TEST_H_ -#define DETERMINIZE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class determinizeTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( determinizeTest ); - CPPUNIT_TEST( testDeterminizeNFA ); - CPPUNIT_TEST( testDeterminizeIDPDA ); - CPPUNIT_TEST( testDeterminizeVPA ); - CPPUNIT_TEST( testDeterminizeNFTA ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testDeterminizeNFA(); - void testDeterminizeIDPDA(); - void testDeterminizeVPA(); - void testDeterminizeNFTA(); -}; - -#endif // DETERMINIZE_TEST_H_ diff --git a/alib2algo/test-src/automaton/properties/EpsilonClosureTest.cpp b/alib2algo/test-src/automaton/properties/EpsilonClosureTest.cpp index 6e8de6b68b..55ef1b266d 100644 --- a/alib2algo/test-src/automaton/properties/EpsilonClosureTest.cpp +++ b/alib2algo/test-src/automaton/properties/EpsilonClosureTest.cpp @@ -1,46 +1,39 @@ -#include "EpsilonClosureTest.h" +#include <catch2/catch.hpp> #include <automaton/FSM/EpsilonNFA.h> #include "automaton/properties/EpsilonClosure.h" #include "automaton/properties/AllEpsilonClosure.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( EpsilonClosureTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( EpsilonClosureTest ); - -void EpsilonClosureTest::setUp() { -} - -void EpsilonClosureTest::tearDown() { -} - -void EpsilonClosureTest::testEpsilonClosure() { - DefaultStateType q0 = DefaultStateType ("q0"); - DefaultStateType q1 = DefaultStateType ("q1"); - DefaultStateType q2 = DefaultStateType ("q2"); - DefaultStateType q3 = DefaultStateType ("q3"); - DefaultStateType q4 = DefaultStateType ("q4"); - DefaultStateType q5 = DefaultStateType ("q5"); - DefaultStateType q6 = DefaultStateType ("q6"); - DefaultStateType q7 = DefaultStateType ("q7"); - DefaultStateType q8 = DefaultStateType ("q8"); - DefaultStateType q9 = DefaultStateType ("q9"); - - automaton::EpsilonNFA < > automaton(q0); - automaton.setStates({q0, q1, q2, q3, q4, q5, q6, q7, q8, q9}); - - automaton.addTransition(q0, q1); - automaton.addTransition(q1, q2); - automaton.addTransition(q2, q3); - automaton.addTransition(q3, q4); - automaton.addTransition(q4, q1); - automaton.addTransition(q5, q6); - automaton.addTransition(q6, q1); - automaton.addTransition(q8, q8); - - ext::map<DefaultStateType, ext::set<DefaultStateType>> allClosures = automaton::properties::AllEpsilonClosure::allEpsilonClosure(automaton); - - for(const DefaultStateType& state : automaton.getStates()) { - CPPUNIT_ASSERT(automaton::properties::EpsilonClosure::epsilonClosure(automaton, state) == allClosures[state]); +TEST_CASE ( "Epsilon Closure", "[unit][algo][automaton]" ) { + SECTION ( "Test closure" ) { + DefaultStateType q0 = DefaultStateType ("q0"); + DefaultStateType q1 = DefaultStateType ("q1"); + DefaultStateType q2 = DefaultStateType ("q2"); + DefaultStateType q3 = DefaultStateType ("q3"); + DefaultStateType q4 = DefaultStateType ("q4"); + DefaultStateType q5 = DefaultStateType ("q5"); + DefaultStateType q6 = DefaultStateType ("q6"); + DefaultStateType q7 = DefaultStateType ("q7"); + DefaultStateType q8 = DefaultStateType ("q8"); + DefaultStateType q9 = DefaultStateType ("q9"); + + automaton::EpsilonNFA < > automaton(q0); + automaton.setStates({q0, q1, q2, q3, q4, q5, q6, q7, q8, q9}); + + automaton.addTransition(q0, q1); + automaton.addTransition(q1, q2); + automaton.addTransition(q2, q3); + automaton.addTransition(q3, q4); + automaton.addTransition(q4, q1); + automaton.addTransition(q5, q6); + automaton.addTransition(q6, q1); + automaton.addTransition(q8, q8); + + ext::map<DefaultStateType, ext::set<DefaultStateType>> allClosures = automaton::properties::AllEpsilonClosure::allEpsilonClosure(automaton); + + for(const DefaultStateType& state : automaton.getStates()) { + CHECK(automaton::properties::EpsilonClosure::epsilonClosure(automaton, state) == allClosures[state]); + } } } diff --git a/alib2algo/test-src/automaton/properties/EpsilonClosureTest.h b/alib2algo/test-src/automaton/properties/EpsilonClosureTest.h deleted file mode 100644 index ccb5ed888a..0000000000 --- a/alib2algo/test-src/automaton/properties/EpsilonClosureTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef EPSILON_CLOSURE_TEST_H_ -#define EPSILON_CLOSURE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class EpsilonClosureTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( EpsilonClosureTest ); - CPPUNIT_TEST( testEpsilonClosure ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testEpsilonClosure(); -}; - -#endif /* EPSILON_CLOSURE_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.cpp b/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.cpp index f83491dd1d..49ff418ecd 100644 --- a/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.cpp +++ b/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.cpp @@ -1,4 +1,4 @@ -#include "FSMSingleInitialStateTest.h" +#include <catch2/catch.hpp> #include "automaton/simplify/SingleInitialState.h" #include "automaton/determinize/Determinize.h" @@ -7,48 +7,41 @@ #include "automaton/FSM/MultiInitialStateNFA.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( FSMSingleInitialStateTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( FSMSingleInitialStateTest ); - -void FSMSingleInitialStateTest::setUp() { -} - -void FSMSingleInitialStateTest::tearDown() { -} - -void FSMSingleInitialStateTest::testSingleInitialState() { - DefaultStateType q = DefaultStateType ("q"); - DefaultStateType q0 = DefaultStateType ("q0"); - DefaultStateType q1 = DefaultStateType ("q1"); - DefaultStateType q2 = DefaultStateType ("q2"); - DefaultStateType q3 = DefaultStateType ("q3"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - automaton::MultiInitialStateNFA < > automaton1; - automaton1.setStates({q0, q1, q2, q3}); - automaton1.setInitialStates({q0, q1, q2}); - automaton1.setFinalStates({q3}); - automaton1.setInputAlphabet({a, b}); - automaton1.addTransition(q0, a, q1); - automaton1.addTransition(q1, b, q2); - automaton1.addTransition(q2, a, q3); - - automaton::NFA < > automaton2 = automaton::simplify::SingleInitialState::convert(automaton1); - - automaton::NFA < > automaton3(q); - automaton3.setStates({q, q1, q2, q3}); - automaton3.setFinalStates({q3}); - automaton3.setInputAlphabet({a, b}); - automaton3.addTransition(q, a, q3); - automaton3.addTransition(q, b, q2); - automaton3.addTransition(q, a, q1); - automaton3.addTransition(q1, b, q2); - automaton3.addTransition(q2, a, q3); - - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa2 = automaton::simplify::Minimize::minimize(automaton::determinize::Determinize::determinize(automaton2)); - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa3 = automaton::simplify::Minimize::minimize(automaton::determinize::Determinize::determinize(automaton3)); - - CPPUNIT_ASSERT(automaton::simplify::Normalize::normalize(dfa2) == automaton::simplify::Normalize::normalize(dfa3)); +TEST_CASE ( "FSM Single initial state", "[unit][algo][automaton][simplify]" ) { + SECTION ( "MISNFA to single initial state NFA" ) { + DefaultStateType q = DefaultStateType ("q"); + DefaultStateType q0 = DefaultStateType ("q0"); + DefaultStateType q1 = DefaultStateType ("q1"); + DefaultStateType q2 = DefaultStateType ("q2"); + DefaultStateType q3 = DefaultStateType ("q3"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + automaton::MultiInitialStateNFA < > automaton1; + automaton1.setStates({q0, q1, q2, q3}); + automaton1.setInitialStates({q0, q1, q2}); + automaton1.setFinalStates({q3}); + automaton1.setInputAlphabet({a, b}); + automaton1.addTransition(q0, a, q1); + automaton1.addTransition(q1, b, q2); + automaton1.addTransition(q2, a, q3); + + automaton::NFA < > automaton2 = automaton::simplify::SingleInitialState::convert(automaton1); + + automaton::NFA < > automaton3(q); + automaton3.setStates({q, q1, q2, q3}); + automaton3.setFinalStates({q3}); + automaton3.setInputAlphabet({a, b}); + automaton3.addTransition(q, a, q3); + automaton3.addTransition(q, b, q2); + automaton3.addTransition(q, a, q1); + automaton3.addTransition(q1, b, q2); + automaton3.addTransition(q2, a, q3); + + automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa2 = automaton::simplify::Minimize::minimize(automaton::determinize::Determinize::determinize(automaton2)); + automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa3 = automaton::simplify::Minimize::minimize(automaton::determinize::Determinize::determinize(automaton3)); + + CHECK (automaton::simplify::Normalize::normalize(dfa2) == automaton::simplify::Normalize::normalize(dfa3)); + } } diff --git a/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.h b/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.h deleted file mode 100644 index fee9a58ef3..0000000000 --- a/alib2algo/test-src/automaton/simplify/FSMSingleInitialStateTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef FSM_SINGLE_INITIAL_STATE_TEST_H_ -#define FSM_SINGLE_INITIAL_STATE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class FSMSingleInitialStateTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( FSMSingleInitialStateTest ); - CPPUNIT_TEST( testSingleInitialState ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testSingleInitialState(); -}; - -#endif /* FSM_SINGLE_INITIAL_STATE_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/simplify/FSMTotalTest.cpp b/alib2algo/test-src/automaton/simplify/FSMTotalTest.cpp index 0cfecbd2d7..644381cb32 100644 --- a/alib2algo/test-src/automaton/simplify/FSMTotalTest.cpp +++ b/alib2algo/test-src/automaton/simplify/FSMTotalTest.cpp @@ -1,4 +1,4 @@ -#include "FSMTotalTest.h" +#include <catch2/catch.hpp> #include <automaton/FSM/DFA.h> @@ -6,41 +6,34 @@ #include "automaton/simplify/Normalize.h" #include "automaton/simplify/Trim.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( TotalTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( TotalTest ); +TEST_CASE ( "Total automaton", "[unit][algo][automaton][simplify]" ) { + SECTION ( "DFA to DFA with total transition function" ) { + DefaultStateType q0 = DefaultStateType ("q0"); + DefaultStateType q1 = DefaultStateType ("q1"); + DefaultStateType q2 = DefaultStateType ("q2"); -void TotalTest::setUp() { -} - -void TotalTest::tearDown() { -} - -void TotalTest::testTotal() { - DefaultStateType q0 = DefaultStateType ("q0"); - DefaultStateType q1 = DefaultStateType ("q1"); - DefaultStateType q2 = DefaultStateType ("q2"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); - automaton::DFA<> automaton(q0); - automaton.setStates({q0, q1, q2}); - automaton.setFinalStates({q0, q1, q2}); - automaton.setInputAlphabet({a, b, c}); + automaton::DFA<> automaton(q0); + automaton.setStates({q0, q1, q2}); + automaton.setFinalStates({q0, q1, q2}); + automaton.setInputAlphabet({a, b, c}); - automaton.addTransition(q0, a, q0); - automaton.addTransition(q0, b, q1); - automaton.addTransition(q0, c, q2); - automaton.addTransition(q1, b, q1); - automaton.addTransition(q1, c, q2); - automaton.addTransition(q2, c, q2); + automaton.addTransition(q0, a, q0); + automaton.addTransition(q0, b, q1); + automaton.addTransition(q0, c, q2); + automaton.addTransition(q1, b, q1); + automaton.addTransition(q1, c, q2); + automaton.addTransition(q2, c, q2); - automaton::DFA<> totalAutomaton = automaton::simplify::Total::total(automaton); - CPPUNIT_ASSERT(totalAutomaton.isTotal()); + automaton::DFA<> totalAutomaton = automaton::simplify::Total::total(automaton); + CHECK(totalAutomaton.isTotal()); - automaton::DFA<> trimmedAutomaton = automaton::simplify::Trim::trim(automaton); - automaton::DFA<> trimmedTotalAutomaton = automaton::simplify::Trim::trim(totalAutomaton); + automaton::DFA<> trimmedAutomaton = automaton::simplify::Trim::trim(automaton); + automaton::DFA<> trimmedTotalAutomaton = automaton::simplify::Trim::trim(totalAutomaton); - CPPUNIT_ASSERT(automaton::simplify::Normalize::normalize(trimmedAutomaton) == automaton::simplify::Normalize::normalize(trimmedTotalAutomaton)); + CHECK(automaton::simplify::Normalize::normalize(trimmedAutomaton) == automaton::simplify::Normalize::normalize(trimmedTotalAutomaton)); + } } diff --git a/alib2algo/test-src/automaton/simplify/FSMTotalTest.h b/alib2algo/test-src/automaton/simplify/FSMTotalTest.h deleted file mode 100644 index 1a7b09f16d..0000000000 --- a/alib2algo/test-src/automaton/simplify/FSMTotalTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef FSM_TOTAL_TEST_H_ -#define FSM_TOTAL_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class TotalTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( TotalTest ); - CPPUNIT_TEST( testTotal ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testTotal(); -}; - -#endif /* FSM_TOTAL_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.cpp b/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.cpp index 1ecee1151a..dd7fe5f2b8 100644 --- a/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.cpp +++ b/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.cpp @@ -1,37 +1,31 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "minimizeBrzozowskiTest.h" #include "automaton/simplify/MinimizeBrzozowski.h" #include "automaton/simplify/Minimize.h" #include "automaton/simplify/Trim.h" #include "automaton/simplify/Normalize.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( minimizeBrzozowskiTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( minimizeBrzozowskiTest ); +TEST_CASE ( "Brzozowski minimization", "[unit][algo][automaton][simplify]" ) { + SECTION ( "Test DFA" ) { + automaton::DFA < > automaton(DefaultStateType(1)); -void minimizeBrzozowskiTest::setUp() { -} + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); -void minimizeBrzozowskiTest::tearDown() { -} + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); + automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); + + automaton.addFinalState(DefaultStateType(3)); + + automaton::DFA < > minimizedHopcroft = automaton::simplify::Minimize::minimize(automaton); + automaton::DFA < DefaultSymbolType, ext::set < ext::set < DefaultStateType > > > minimizedBrzozowski = automaton::simplify::MinimizeBrzozowski::minimize(automaton); -void minimizeBrzozowskiTest::testMinimizeBrzozowski() { - automaton::DFA < > automaton(DefaultStateType(1)); - - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); - - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); - automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); - - automaton.addFinalState(DefaultStateType(3)); - - automaton::DFA < > minimizedHopcroft = automaton::simplify::Minimize::minimize(automaton); - automaton::DFA < DefaultSymbolType, ext::set < ext::set < DefaultStateType > > > minimizedBrzozowski = automaton::simplify::MinimizeBrzozowski::minimize(automaton); - - CPPUNIT_ASSERT(minimizedHopcroft.getStates().size() == 3); - CPPUNIT_ASSERT(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(minimizedHopcroft)) == automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(minimizedBrzozowski))); + CHECK(minimizedHopcroft.getStates().size() == 3); + CHECK(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(minimizedHopcroft)) == automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(minimizedBrzozowski))); + } } diff --git a/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.h b/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.h deleted file mode 100644 index 0039075c8b..0000000000 --- a/alib2algo/test-src/automaton/simplify/minimizeBrzozowskiTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef MINIMIZE_BRZOZOWSKI_TEST_H_ -#define MINIMIZE_BRZOZOWSKI_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class minimizeBrzozowskiTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( minimizeBrzozowskiTest ); - CPPUNIT_TEST( testMinimizeBrzozowski ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testMinimizeBrzozowski(); -}; - -#endif // MINIMIZE_BRZOZOWSKI_TEST_H_ diff --git a/alib2algo/test-src/automaton/simplify/minimizeTest.cpp b/alib2algo/test-src/automaton/simplify/minimizeTest.cpp index 2f653fca81..5583ff41d1 100644 --- a/alib2algo/test-src/automaton/simplify/minimizeTest.cpp +++ b/alib2algo/test-src/automaton/simplify/minimizeTest.cpp @@ -1,178 +1,172 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "minimizeTest.h" #include "automaton/simplify/Minimize.h" #include <factory/XmlDataFactory.hpp> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( minimizeTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( minimizeTest ); - -void minimizeTest::setUp() { -} - -void minimizeTest::tearDown() { -} +TEST_CASE ( "Minimization", "[unit][algo][automaton][simplify]" ) { + SECTION ( "DFA" ) { + automaton::DFA < > automaton(DefaultStateType(1)); -void minimizeTest::testMinimizeDFA() { - automaton::DFA < > automaton(DefaultStateType(1)); + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); + automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); - automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); + automaton.addFinalState(DefaultStateType(3)); - automaton.addFinalState(DefaultStateType(3)); + automaton::DFA<> minimized = automaton::simplify::Minimize::minimize(automaton); - automaton::DFA<> minimized = automaton::simplify::Minimize::minimize(automaton); + CHECK(minimized.getStates().size() == 3); - CPPUNIT_ASSERT(minimized.getStates().size() == 3); - -} + } -void minimizeTest::testMinimizeDFTA() { - automaton::DFTA < > automaton; + SECTION ( "DFTA" ) { + automaton::DFTA < > automaton; - ext::vector<DefaultStateType> q; + ext::vector<DefaultStateType> q; - for (int i = 0; i <= 10; ++i) { - DefaultStateType state (i); - q.push_back(state); - automaton.addState(state); - } + for (int i = 0; i <= 10; ++i) { + DefaultStateType state (i); + q.push_back(state); + automaton.addState(state); + } - automaton.addFinalState(q[9]); - automaton.addFinalState(q[10]); - - const common::ranked_symbol < > a (DefaultSymbolType("a"), DefaultRankType(3)); - const common::ranked_symbol < > b (DefaultSymbolType("b"), DefaultRankType(2)); - const common::ranked_symbol < > c (DefaultSymbolType("c"), DefaultRankType(1)); - const common::ranked_symbol < > d (DefaultSymbolType("d"), DefaultRankType(0)); - const common::ranked_symbol < > e (DefaultSymbolType("e"), DefaultRankType(0)); - const common::ranked_symbol < > f (DefaultSymbolType("f"), DefaultRankType(0)); - const common::ranked_symbol < > g (DefaultSymbolType("g"), DefaultRankType(0)); - - automaton.addInputSymbol(a); - automaton.addInputSymbol(b); - automaton.addInputSymbol(c); - automaton.addInputSymbol(d); - automaton.addInputSymbol(e); - automaton.addInputSymbol(f); - automaton.addInputSymbol(g); - - automaton.addTransition(d, {}, q[0]); - automaton.addTransition(e, {}, q[1]); - - for (int i = 0; i <= 1; ++i) { - for (int j = 0; j <= 1; ++j) { - automaton.addTransition(b, {q[i], q[j]}, q[2]); + automaton.addFinalState(q[9]); + automaton.addFinalState(q[10]); + + const common::ranked_symbol < > a (DefaultSymbolType("a"), DefaultRankType(3)); + const common::ranked_symbol < > b (DefaultSymbolType("b"), DefaultRankType(2)); + const common::ranked_symbol < > c (DefaultSymbolType("c"), DefaultRankType(1)); + const common::ranked_symbol < > d (DefaultSymbolType("d"), DefaultRankType(0)); + const common::ranked_symbol < > e (DefaultSymbolType("e"), DefaultRankType(0)); + const common::ranked_symbol < > f (DefaultSymbolType("f"), DefaultRankType(0)); + const common::ranked_symbol < > g (DefaultSymbolType("g"), DefaultRankType(0)); + + automaton.addInputSymbol(a); + automaton.addInputSymbol(b); + automaton.addInputSymbol(c); + automaton.addInputSymbol(d); + automaton.addInputSymbol(e); + automaton.addInputSymbol(f); + automaton.addInputSymbol(g); + + automaton.addTransition(d, {}, q[0]); + automaton.addTransition(e, {}, q[1]); + + for (int i = 0; i <= 1; ++i) { + for (int j = 0; j <= 1; ++j) { + automaton.addTransition(b, {q[i], q[j]}, q[2]); + } } - } - automaton.addTransition(b, {q[2], q[2]}, q[6]); - automaton.addTransition(f, {}, q[3]); - for (int i = 3; i < 5; ++i) { - automaton.addTransition(c, {q[i]}, q[i+1]); - } + automaton.addTransition(b, {q[2], q[2]}, q[6]); + automaton.addTransition(f, {}, q[3]); + for (int i = 3; i < 5; ++i) { + automaton.addTransition(c, {q[i]}, q[i+1]); + } - automaton.addTransition(c, {q[5]}, q[7]); - automaton.addTransition(g, {}, q[8]); + automaton.addTransition(c, {q[5]}, q[7]); + automaton.addTransition(g, {}, q[8]); - for (int i = 6; i <= 8; ++i) { - for (int j = 6; j <= 8; ++j) { - for (int k = 6; k <= 8; ++k) { - automaton.addTransition(a, {q[i], q[j], q[k]}, q[9]); + for (int i = 6; i <= 8; ++i) { + for (int j = 6; j <= 8; ++j) { + for (int k = 6; k <= 8; ++k) { + automaton.addTransition(a, {q[i], q[j], q[k]}, q[9]); + } } } - } - automaton.addTransition(a, {q[9], q[9], q[9]}, q[10]); - - automaton::DFTA < > minimal; - minimal.addState(q[0]); - minimal.addState(q[2]); - minimal.addState(q[3]); - minimal.addState(q[4]); - minimal.addState(q[5]); - minimal.addState(q[6]); - minimal.addState(q[9]); - minimal.addState(q[10]); - minimal.setFinalStates(automaton.getFinalStates()); - minimal.setInputAlphabet(automaton.getInputAlphabet()); - minimal.addTransition(d, {}, q[0]); - minimal.addTransition(e, {}, q[0]); - minimal.addTransition(b, {q[0], q[0]}, q[2]); - minimal.addTransition(b, {q[2], q[2]}, q[6]); - minimal.addTransition(f, {}, q[3]); - - for (int i = 3; i < 5; ++i) { - minimal.addTransition(c, {q[i]}, q[i+1]); - } + automaton.addTransition(a, {q[9], q[9], q[9]}, q[10]); + + automaton::DFTA < > minimal; + minimal.addState(q[0]); + minimal.addState(q[2]); + minimal.addState(q[3]); + minimal.addState(q[4]); + minimal.addState(q[5]); + minimal.addState(q[6]); + minimal.addState(q[9]); + minimal.addState(q[10]); + minimal.setFinalStates(automaton.getFinalStates()); + minimal.setInputAlphabet(automaton.getInputAlphabet()); + minimal.addTransition(d, {}, q[0]); + minimal.addTransition(e, {}, q[0]); + minimal.addTransition(b, {q[0], q[0]}, q[2]); + minimal.addTransition(b, {q[2], q[2]}, q[6]); + minimal.addTransition(f, {}, q[3]); + + for (int i = 3; i < 5; ++i) { + minimal.addTransition(c, {q[i]}, q[i+1]); + } - minimal.addTransition(c, {q[5]}, q[6]); - minimal.addTransition(g, {}, q[6]); - minimal.addTransition(a, {q[6], q[6], q[6]}, q[9]); - minimal.addTransition(a, {q[9], q[9], q[9]}, q[10]); - - automaton::DFTA<> minimized = automaton::simplify::Minimize::minimize(automaton); - CPPUNIT_ASSERT(minimized == minimal); - -/* automaton::DFTA < > automaton; - - const DefaultStateType q0 ("0"); - const DefaultStateType q1 ("1"); - const DefaultStateType q00 ("00"); - const DefaultStateType q11 ("11"); - automaton.addState(q0); - automaton.addState(q1); - automaton.addState(q00); - automaton.addState(q11); - - const common::ranked_symbol < > st ("t", 0); - const common::ranked_symbol < > sf ("f", 0); - const common::ranked_symbol < > snot ("not", 1); - const common::ranked_symbol < > sor ("or", 2); - automaton.addInputSymbol(st); - automaton.addInputSymbol(sf); - automaton.addInputSymbol(snot); - automaton.addInputSymbol(sor); - - automaton.addTransition(st, {}, q1); - automaton.addTransition(sf, {}, q0); - - automaton.addTransition(snot, {q0}, q1); - automaton.addTransition(snot, {q1}, q0); - automaton.addTransition(snot, {q00}, q1); - automaton.addTransition(snot, {q11}, q0); - - automaton.addTransition(sor, {q0, q0}, q00); - automaton.addTransition(sor, {q0, q00}, q00); - automaton.addTransition(sor, {q00, q0}, q00); - automaton.addTransition(sor, {q00, q00}, q00); - automaton.addTransition(sor, {q0, q1}, q1); - automaton.addTransition(sor, {q0, q11}, q1); - automaton.addTransition(sor, {q00, q1}, q1); - automaton.addTransition(sor, {q00, q11}, q1); - automaton.addTransition(sor, {q1, q0}, q1); - automaton.addTransition(sor, {q1, q00}, q1); - automaton.addTransition(sor, {q11, q0}, q1); - automaton.addTransition(sor, {q11, q00}, q1); - automaton.addTransition(sor, {q1, q1}, q11); - automaton.addTransition(sor, {q1, q11}, q11); - automaton.addTransition(sor, {q11, q1}, q11); - automaton.addTransition(sor, {q11, q11}, q11); - - automaton.addFinalState(q1); - automaton.addFinalState(q11); - - automaton::DFTA<> minimized = automaton::simplify::Minimize::minimize(automaton); - std::cout << minimized << std::endl; - CPPUNIT_ASSERT(minimized.getStates().size() == 2); - CPPUNIT_ASSERT(minimized.getFinalStates().size() == 1); - CPPUNIT_ASSERT(minimized.getTransitions().size() == 8); - CPPUNIT_ASSERT(minimized.getInputAlphabet().size() == 4); -*/ + minimal.addTransition(c, {q[5]}, q[6]); + minimal.addTransition(g, {}, q[6]); + minimal.addTransition(a, {q[6], q[6], q[6]}, q[9]); + minimal.addTransition(a, {q[9], q[9], q[9]}, q[10]); + + automaton::DFTA<> minimized = automaton::simplify::Minimize::minimize(automaton); + CHECK(minimized == minimal); + + /* automaton::DFTA < > automaton; + + const DefaultStateType q0 ("0"); + const DefaultStateType q1 ("1"); + const DefaultStateType q00 ("00"); + const DefaultStateType q11 ("11"); + automaton.addState(q0); + automaton.addState(q1); + automaton.addState(q00); + automaton.addState(q11); + + const common::ranked_symbol < > st ("t", 0); + const common::ranked_symbol < > sf ("f", 0); + const common::ranked_symbol < > snot ("not", 1); + const common::ranked_symbol < > sor ("or", 2); + automaton.addInputSymbol(st); + automaton.addInputSymbol(sf); + automaton.addInputSymbol(snot); + automaton.addInputSymbol(sor); + + automaton.addTransition(st, {}, q1); + automaton.addTransition(sf, {}, q0); + + automaton.addTransition(snot, {q0}, q1); + automaton.addTransition(snot, {q1}, q0); + automaton.addTransition(snot, {q00}, q1); + automaton.addTransition(snot, {q11}, q0); + + automaton.addTransition(sor, {q0, q0}, q00); + automaton.addTransition(sor, {q0, q00}, q00); + automaton.addTransition(sor, {q00, q0}, q00); + automaton.addTransition(sor, {q00, q00}, q00); + automaton.addTransition(sor, {q0, q1}, q1); + automaton.addTransition(sor, {q0, q11}, q1); + automaton.addTransition(sor, {q00, q1}, q1); + automaton.addTransition(sor, {q00, q11}, q1); + automaton.addTransition(sor, {q1, q0}, q1); + automaton.addTransition(sor, {q1, q00}, q1); + automaton.addTransition(sor, {q11, q0}, q1); + automaton.addTransition(sor, {q11, q00}, q1); + automaton.addTransition(sor, {q1, q1}, q11); + automaton.addTransition(sor, {q1, q11}, q11); + automaton.addTransition(sor, {q11, q1}, q11); + automaton.addTransition(sor, {q11, q11}, q11); + + automaton.addFinalState(q1); + automaton.addFinalState(q11); + + automaton::DFTA<> minimized = automaton::simplify::Minimize::minimize(automaton); + std::cout << minimized << std::endl; + CPPUNIT_ASSERT(minimized.getStates().size() == 2); + CPPUNIT_ASSERT(minimized.getFinalStates().size() == 1); + CPPUNIT_ASSERT(minimized.getTransitions().size() == 8); + CPPUNIT_ASSERT(minimized.getInputAlphabet().size() == 4); + */ + } } diff --git a/alib2algo/test-src/automaton/simplify/minimizeTest.h b/alib2algo/test-src/automaton/simplify/minimizeTest.h deleted file mode 100644 index 50813dbd68..0000000000 --- a/alib2algo/test-src/automaton/simplify/minimizeTest.h +++ /dev/null @@ -1,20 +0,0 @@ -#ifndef MINIMIZE_TEST_H_ -#define MINIMIZE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class minimizeTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE( minimizeTest ); - CPPUNIT_TEST( testMinimizeDFA ); - CPPUNIT_TEST( testMinimizeDFTA ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testMinimizeDFA(); - void testMinimizeDFTA(); -}; - -#endif // MINIMIZE_TEST_H_ diff --git a/alib2algo/test-src/automaton/simplify/normalizeTest.cpp b/alib2algo/test-src/automaton/simplify/normalizeTest.cpp index b45dc838cc..8422c1ad82 100644 --- a/alib2algo/test-src/automaton/simplify/normalizeTest.cpp +++ b/alib2algo/test-src/automaton/simplify/normalizeTest.cpp @@ -1,49 +1,42 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "normalizeTest.h" #include "automaton/simplify/Normalize.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( normalizeTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( normalizeTest ); - -void normalizeTest::setUp() { -} - -void normalizeTest::tearDown() { -} - -void normalizeTest::testNormalize() { - automaton::DFA < > automaton(DefaultStateType(0)); - - automaton.addState(DefaultStateType(0)); - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); +TEST_CASE ( "Normalize", "[unit][algo][automaton][simplify]" ) { + SECTION ( "DFA" ) { + automaton::DFA < > automaton(DefaultStateType(0)); - automaton.addTransition(DefaultStateType(0), DefaultSymbolType("a"), DefaultStateType(1)); - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("b"), DefaultStateType(2)); + automaton.addState(DefaultStateType(0)); + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); - automaton.addFinalState(DefaultStateType(2)); + automaton.addTransition(DefaultStateType(0), DefaultSymbolType("a"), DefaultStateType(1)); + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("b"), DefaultStateType(2)); - automaton::DFA < DefaultSymbolType, unsigned > normalized = automaton::simplify::Normalize::normalize(automaton); + automaton.addFinalState(DefaultStateType(2)); - CPPUNIT_ASSERT(normalized.getStates().size() == automaton.getStates().size()); + automaton::DFA < DefaultSymbolType, unsigned > normalized = automaton::simplify::Normalize::normalize(automaton); - CPPUNIT_ASSERT(normalized.getTransitions().size() == automaton.getTransitions().size()); + CHECK(normalized.getStates().size() == automaton.getStates().size()); + CHECK(normalized.getTransitions().size() == automaton.getTransitions().size()); - automaton::DFA < DefaultSymbolType, unsigned > reference(0); + automaton::DFA < DefaultSymbolType, unsigned > reference(0); - reference.addState(0); - reference.addState(1); - reference.addState(2); - reference.addInputSymbol(DefaultSymbolType("a")); - reference.addInputSymbol(DefaultSymbolType("b")); + reference.addState(0); + reference.addState(1); + reference.addState(2); + reference.addInputSymbol(DefaultSymbolType("a")); + reference.addInputSymbol(DefaultSymbolType("b")); - reference.addTransition(0, DefaultSymbolType("a"), 1); - reference.addTransition(1, DefaultSymbolType("b"), 2); + reference.addTransition(0, DefaultSymbolType("a"), 1); + reference.addTransition(1, DefaultSymbolType("b"), 2); - reference.addFinalState(2); + reference.addFinalState(2); - CPPUNIT_ASSERT ( normalized == reference ); + CHECK ( normalized == reference ); + } } diff --git a/alib2algo/test-src/automaton/simplify/normalizeTest.h b/alib2algo/test-src/automaton/simplify/normalizeTest.h deleted file mode 100644 index 3f915a4861..0000000000 --- a/alib2algo/test-src/automaton/simplify/normalizeTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef NORMALIZE_TEST_H_ -#define NORMALIZE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class normalizeTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( normalizeTest ); - CPPUNIT_TEST( testNormalize ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testNormalize(); -}; - -#endif // NORMALIZE_TEST_H_ diff --git a/alib2algo/test-src/automaton/simplify/trimTest.cpp b/alib2algo/test-src/automaton/simplify/trimTest.cpp index c2be0d96e5..bf7f50f8d0 100644 --- a/alib2algo/test-src/automaton/simplify/trimTest.cpp +++ b/alib2algo/test-src/automaton/simplify/trimTest.cpp @@ -1,116 +1,83 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "trimTest.h" #include "automaton/simplify/Trim.h" -#include "grammar/simplify/Trim.h" #include "automaton/FSM/DFA.h" -#include "grammar/Regular/RightRG.h" #include "automaton/TA/DFTA.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( trimTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( trimTest ); - -void trimTest::setUp() { -} - -void trimTest::tearDown() { -} - -void trimTest::testTrimAutomaton() { - automaton::DFA < > automaton(DefaultStateType(1)); - - automaton.addState(DefaultStateType(1)); - automaton.addState(DefaultStateType(2)); - automaton.addState(DefaultStateType(3)); - automaton.addInputSymbol(DefaultSymbolType("a")); - automaton.addInputSymbol(DefaultSymbolType("b")); +TEST_CASE ( "Trim Automaton", "[unit][algo][automaton][simplify]" ) { + SECTION ( "DFA" ) { + automaton::DFA < > automaton(DefaultStateType(1)); - automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); - automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); - automaton.addTransition(DefaultStateType(3), DefaultSymbolType("b"), DefaultStateType(1)); + automaton.addState(DefaultStateType(1)); + automaton.addState(DefaultStateType(2)); + automaton.addState(DefaultStateType(3)); + automaton.addInputSymbol(DefaultSymbolType("a")); + automaton.addInputSymbol(DefaultSymbolType("b")); - automaton.addFinalState(DefaultStateType(1)); + automaton.addTransition(DefaultStateType(1), DefaultSymbolType("a"), DefaultStateType(2)); + automaton.addTransition(DefaultStateType(2), DefaultSymbolType("b"), DefaultStateType(1)); + automaton.addTransition(DefaultStateType(3), DefaultSymbolType("b"), DefaultStateType(1)); - automaton::DFA<> trimed = automaton::simplify::Trim::trim(automaton); + automaton.addFinalState(DefaultStateType(1)); - CPPUNIT_ASSERT(trimed.getStates().size() == 2); -} + automaton::DFA<> trimed = automaton::simplify::Trim::trim(automaton); -void trimTest::testTrimGrammar() { - grammar::RightRG < > rrGrammar(DefaultSymbolType(1)); - - rrGrammar.addNonterminalSymbol(DefaultSymbolType(1)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(4)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(5)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(6)); - rrGrammar.addTerminalSymbol(DefaultSymbolType("a")); - rrGrammar.addTerminalSymbol(DefaultSymbolType("b")); - - rrGrammar.addRule(DefaultSymbolType(1), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); - rrGrammar.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); - rrGrammar.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); - - rrGrammar.addRule(DefaultSymbolType(4), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(5))); - rrGrammar.addRule(DefaultSymbolType(5), DefaultSymbolType("a")); - rrGrammar.addRule(DefaultSymbolType(5), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(2))); - rrGrammar.addRule(DefaultSymbolType(6), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(6))); - - grammar::RightRG < > trimed = grammar::simplify::Trim::trim(rrGrammar); - - CPPUNIT_ASSERT(trimed.getNonterminalAlphabet().size() == 3); -} + CHECK (trimed.getStates().size() == 2); + } -void trimTest::testTrimDFTA() { - automaton::DFTA < > automaton; - ext::vector<DefaultStateType> q; - for (int i = 0; i <= 11; ++i) { - DefaultStateType state (i); - q.push_back(state); - automaton.addState(state); + SECTION ( "DFTA" ) { + automaton::DFTA < > automaton; + + ext::vector<DefaultStateType> q; + for (int i = 0; i <= 11; ++i) { + DefaultStateType state (i); + q.push_back(state); + automaton.addState(state); + } + automaton.addFinalState(q[2]); + automaton.addFinalState(q[11]); + + const common::ranked_symbol < > a (DefaultSymbolType("a"), DefaultRankType(2)); + const common::ranked_symbol < > b (DefaultSymbolType("b"), DefaultRankType(1)); + const common::ranked_symbol < > c (DefaultSymbolType("c"), DefaultRankType(0)); + automaton.addInputSymbol(a); + automaton.addInputSymbol(b); + automaton.addInputSymbol(c); + + automaton.addTransition(c, {}, q[0]); + automaton.addTransition(a, {q[0], q[0]}, q[1]); + automaton.addTransition(b, {q[1]}, q[2]); + + //unreachable and useless + automaton.addTransition(a, {q[3], q[4]}, q[5]); + automaton.addTransition(b, {q[5]}, q[6]); + + //useless + automaton.addTransition(a, {q[2], q[2]}, q[7]); + automaton.addTransition(a, {q[7], q[7]}, q[8]); + + //unreachable + automaton.addTransition(a, {q[9], q[9]}, q[10]); + automaton.addTransition(a, {q[10], q[10]}, q[11]); + + automaton::DFTA<> trimed = automaton::simplify::Trim::trim(automaton); + + automaton::DFTA<> correct; + correct.addState(q[0]); + correct.addState(q[1]); + correct.addState(q[2]); + correct.addFinalState(q[2]); + correct.addInputSymbol(a); + correct.addInputSymbol(b); + correct.addInputSymbol(c); + correct.addTransition(c, {}, q[0]); + correct.addTransition(a, {q[0], q[0]}, q[1]); + correct.addTransition(b, {q[1]}, q[2]); + + CHECK (trimed == correct); } - automaton.addFinalState(q[2]); - automaton.addFinalState(q[11]); - - const common::ranked_symbol < > a (DefaultSymbolType("a"), DefaultRankType(2)); - const common::ranked_symbol < > b (DefaultSymbolType("b"), DefaultRankType(1)); - const common::ranked_symbol < > c (DefaultSymbolType("c"), DefaultRankType(0)); - automaton.addInputSymbol(a); - automaton.addInputSymbol(b); - automaton.addInputSymbol(c); - - automaton.addTransition(c, {}, q[0]); - automaton.addTransition(a, {q[0], q[0]}, q[1]); - automaton.addTransition(b, {q[1]}, q[2]); - - //unreachable and useless - automaton.addTransition(a, {q[3], q[4]}, q[5]); - automaton.addTransition(b, {q[5]}, q[6]); - - //useless - automaton.addTransition(a, {q[2], q[2]}, q[7]); - automaton.addTransition(a, {q[7], q[7]}, q[8]); - - //unreachable - automaton.addTransition(a, {q[9], q[9]}, q[10]); - automaton.addTransition(a, {q[10], q[10]}, q[11]); - - automaton::DFTA<> trimed = automaton::simplify::Trim::trim(automaton); - - automaton::DFTA<> correct; - correct.addState(q[0]); - correct.addState(q[1]); - correct.addState(q[2]); - correct.addFinalState(q[2]); - correct.addInputSymbol(a); - correct.addInputSymbol(b); - correct.addInputSymbol(c); - correct.addTransition(c, {}, q[0]); - correct.addTransition(a, {q[0], q[0]}, q[1]); - correct.addTransition(b, {q[1]}, q[2]); - - CPPUNIT_ASSERT(trimed == correct); } diff --git a/alib2algo/test-src/automaton/simplify/trimTest.h b/alib2algo/test-src/automaton/simplify/trimTest.h deleted file mode 100644 index 79b6736ce6..0000000000 --- a/alib2algo/test-src/automaton/simplify/trimTest.h +++ /dev/null @@ -1,22 +0,0 @@ -#ifndef TRIM_TEST_H_ -#define TRIM_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class trimTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE( trimTest ); - CPPUNIT_TEST( testTrimAutomaton ); - CPPUNIT_TEST( testTrimGrammar ); - CPPUNIT_TEST( testTrimDFTA ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testTrimAutomaton(); - void testTrimGrammar(); - void testTrimDFTA(); -}; - -#endif // TRIM_TEST_H_ diff --git a/alib2algo/test-src/automaton/transform/AutomataCompactionTest.cpp b/alib2algo/test-src/automaton/transform/AutomataCompactionTest.cpp index 7dd26aa048..3ae781f59b 100644 --- a/alib2algo/test-src/automaton/transform/AutomataCompactionTest.cpp +++ b/alib2algo/test-src/automaton/transform/AutomataCompactionTest.cpp @@ -1,123 +1,114 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "AutomataCompactionTest.h" #include "automaton/transform/Compaction.h" #include <automaton/FSM/DFA.h> #include <automaton/FSM/CompactNFA.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( AutomataCompactionTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( AutomataCompactionTest ); - -void AutomataCompactionTest::setUp() { -} - -void AutomataCompactionTest::tearDown() { -} - -void AutomataCompactionTest::testAutomataCompaction1() { - DefaultStateType q0 = DefaultStateType("0"); - DefaultStateType q1 = DefaultStateType("1"); - DefaultStateType q2 = DefaultStateType("2"); - DefaultStateType q3 = DefaultStateType("3"); - DefaultStateType q4 = DefaultStateType("4"); - DefaultStateType q5 = DefaultStateType("5"); - DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); - - automaton::DFA<> m1(q0); - automaton::CompactNFA < > m2(q0); - - m1.setInputAlphabet({a, b}); - m1.setStates({q0, q1, q2, q3, q4, q5}); - m1.addTransition(q0, a, q1); - m1.addTransition(q1, b, q2); - m1.addTransition(q2, a, q3); - m1.addTransition(q3, b, q4); - m1.addTransition(q4, a, q5); - m1.addFinalState(q5); - - m2.setInputAlphabet({a, b}); - m2.setStates({q0, q5}); - m2.addTransition(q0, ext::vector <DefaultSymbolType > {a, b, a, b, a}, q5); - m2.addFinalState(q5); - - automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); - - CPPUNIT_ASSERT(c1 == m2); - -} - -void AutomataCompactionTest::testAutomataCompaction2() { - DefaultStateType q0 = DefaultStateType("0"); - DefaultStateType q1 = DefaultStateType("1"); - DefaultStateType q2 = DefaultStateType("2"); - DefaultStateType q3 = DefaultStateType("3"); - DefaultStateType q4 = DefaultStateType("4"); - DefaultStateType q5 = DefaultStateType("5"); - DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); - - automaton::DFA<> m1(q0); - automaton::CompactNFA < > m2(q0); - - m1.setInputAlphabet({a, b}); - m1.setStates({q0, q1, q2, q3, q4, q5}); - m1.addTransition(q0, a, q1); - m1.addTransition(q1, b, q2); - m1.addTransition(q2, a, q3); - m1.addTransition(q3, b, q4); - m1.addTransition(q4, a, q5); - m1.addTransition(q5, a, q1); - m1.addFinalState(q5); - - m2.setInputAlphabet({a, b}); - m2.setStates({q0, q5}); - m2.addTransition(q0, ext::vector < DefaultSymbolType > { a, b, a, b, a }, q5); - m2.addTransition(q5, ext::vector < DefaultSymbolType > { a, b, a, b, a }, q5); - m2.addFinalState(q5); - - automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); - - CPPUNIT_ASSERT(c1 == m2); - -} - -void AutomataCompactionTest::testAutomataCompaction3() { - DefaultStateType q0 = DefaultStateType("0"); - DefaultStateType q1 = DefaultStateType("1"); - DefaultStateType q2 = DefaultStateType("2"); - DefaultStateType q3 = DefaultStateType("3"); - DefaultStateType q4 = DefaultStateType("4"); - DefaultStateType q5 = DefaultStateType("5"); - DefaultStateType q6 = DefaultStateType("6"); - DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); - - automaton::DFA<> m1(q0); - automaton::CompactNFA < > m2(q0); - - m1.setInputAlphabet({a, b}); - m1.setStates({q0, q1, q2, q3, q4, q5, q6}); - m1.addTransition(q0, a, q1); - m1.addTransition(q1, a, q2); - m1.addTransition(q2, a, q3); - m1.addTransition(q3, a, q4); - m1.addTransition(q4, a, q2); - m1.addTransition(q1, b, q5); - m1.addTransition(q5, b, q6); - m1.addTransition(q6, a, q0); - m1.addFinalState(q3); - m1.addFinalState(q5); - - m2.setInputAlphabet({a, b}); - m2.setStates({q0, q1, q3, q5}); - m2.addTransition(q0, ext::vector < DefaultSymbolType > {a}, q1); - m2.addTransition(q1, ext::vector < DefaultSymbolType > {a, a}, q3); - m2.addTransition(q3, ext::vector < DefaultSymbolType > {a, a, a}, q3); - m2.addTransition(q1, ext::vector < DefaultSymbolType > {b}, q5); - m2.addTransition(q5, ext::vector < DefaultSymbolType > {b, a, a}, q1); - m2.addFinalState(q3); - m2.addFinalState(q5); - - automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); - - CPPUNIT_ASSERT(c1 == m2); - +TEST_CASE ( "Automata Compaction", "[unit][algo][automaton][transform]" ) { + SECTION ( "DFA" ) { + { + DefaultStateType q0 = DefaultStateType("0"); + DefaultStateType q1 = DefaultStateType("1"); + DefaultStateType q2 = DefaultStateType("2"); + DefaultStateType q3 = DefaultStateType("3"); + DefaultStateType q4 = DefaultStateType("4"); + DefaultStateType q5 = DefaultStateType("5"); + DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); + + automaton::DFA<> m1(q0); + automaton::CompactNFA < > m2(q0); + + m1.setInputAlphabet({a, b}); + m1.setStates({q0, q1, q2, q3, q4, q5}); + m1.addTransition(q0, a, q1); + m1.addTransition(q1, b, q2); + m1.addTransition(q2, a, q3); + m1.addTransition(q3, b, q4); + m1.addTransition(q4, a, q5); + m1.addFinalState(q5); + + m2.setInputAlphabet({a, b}); + m2.setStates({q0, q5}); + m2.addTransition(q0, ext::vector <DefaultSymbolType > {a, b, a, b, a}, q5); + m2.addFinalState(q5); + + automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); + + CHECK (c1 == m2); + }{ + DefaultStateType q0 = DefaultStateType("0"); + DefaultStateType q1 = DefaultStateType("1"); + DefaultStateType q2 = DefaultStateType("2"); + DefaultStateType q3 = DefaultStateType("3"); + DefaultStateType q4 = DefaultStateType("4"); + DefaultStateType q5 = DefaultStateType("5"); + DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); + + automaton::DFA<> m1(q0); + automaton::CompactNFA < > m2(q0); + + m1.setInputAlphabet({a, b}); + m1.setStates({q0, q1, q2, q3, q4, q5}); + m1.addTransition(q0, a, q1); + m1.addTransition(q1, b, q2); + m1.addTransition(q2, a, q3); + m1.addTransition(q3, b, q4); + m1.addTransition(q4, a, q5); + m1.addTransition(q5, a, q1); + m1.addFinalState(q5); + + m2.setInputAlphabet({a, b}); + m2.setStates({q0, q5}); + m2.addTransition(q0, ext::vector < DefaultSymbolType > { a, b, a, b, a }, q5); + m2.addTransition(q5, ext::vector < DefaultSymbolType > { a, b, a, b, a }, q5); + m2.addFinalState(q5); + + automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); + + CHECK (c1 == m2); + + } + { + DefaultStateType q0 = DefaultStateType("0"); + DefaultStateType q1 = DefaultStateType("1"); + DefaultStateType q2 = DefaultStateType("2"); + DefaultStateType q3 = DefaultStateType("3"); + DefaultStateType q4 = DefaultStateType("4"); + DefaultStateType q5 = DefaultStateType("5"); + DefaultStateType q6 = DefaultStateType("6"); + DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); + + automaton::DFA<> m1(q0); + automaton::CompactNFA < > m2(q0); + + m1.setInputAlphabet({a, b}); + m1.setStates({q0, q1, q2, q3, q4, q5, q6}); + m1.addTransition(q0, a, q1); + m1.addTransition(q1, a, q2); + m1.addTransition(q2, a, q3); + m1.addTransition(q3, a, q4); + m1.addTransition(q4, a, q2); + m1.addTransition(q1, b, q5); + m1.addTransition(q5, b, q6); + m1.addTransition(q6, a, q0); + m1.addFinalState(q3); + m1.addFinalState(q5); + + m2.setInputAlphabet({a, b}); + m2.setStates({q0, q1, q3, q5}); + m2.addTransition(q0, ext::vector < DefaultSymbolType > {a}, q1); + m2.addTransition(q1, ext::vector < DefaultSymbolType > {a, a}, q3); + m2.addTransition(q3, ext::vector < DefaultSymbolType > {a, a, a}, q3); + m2.addTransition(q1, ext::vector < DefaultSymbolType > {b}, q5); + m2.addTransition(q5, ext::vector < DefaultSymbolType > {b, a, a}, q1); + m2.addFinalState(q3); + m2.addFinalState(q5); + + automaton::CompactNFA < > c1 = automaton::transform::Compaction::convert(m1); + + CHECK (c1 == m2); + } + } } diff --git a/alib2algo/test-src/automaton/transform/AutomataCompactionTest.h b/alib2algo/test-src/automaton/transform/AutomataCompactionTest.h deleted file mode 100644 index 5f739feed3..0000000000 --- a/alib2algo/test-src/automaton/transform/AutomataCompactionTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef AUTOMATA_COMPACTION_TEST_H_ -#define AUTOMATA_COMPACTION_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class AutomataCompactionTest : public CppUnit::TestFixture { - - CPPUNIT_TEST_SUITE( AutomataCompactionTest ); - CPPUNIT_TEST( testAutomataCompaction1 ); - CPPUNIT_TEST( testAutomataCompaction2 ); - CPPUNIT_TEST( testAutomataCompaction3 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testAutomataCompaction1(); - void testAutomataCompaction2(); - void testAutomataCompaction3(); -}; - -#endif /* AUTOMATA_COMPACTION_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.cpp b/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.cpp index ca08491af2..702b60f084 100644 --- a/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.cpp +++ b/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.cpp @@ -1,5 +1,6 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "AutomataConcatenationTest.h" #include "automaton/transform/AutomataConcatenation.h" #include "automaton/transform/AutomataConcatenationEpsilonTransition.h" @@ -11,79 +12,71 @@ #include "automaton/simplify/Total.h" #include "automaton/determinize/Determinize.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( AutomataConcatenationTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( AutomataConcatenationTest ); - -void AutomataConcatenationTest::setUp() { -} - -void AutomataConcatenationTest::tearDown() { -} - -void AutomataConcatenationTest::testAutomataConcatenation() { - // based on Melichar, 2.79 - - DefaultStateType q1a = DefaultStateType("1"); - DefaultStateType q2a = DefaultStateType("2"); - DefaultStateType q0a = DefaultStateType("0"); - DefaultStateType q1b = DefaultStateType("1'"); - DefaultStateType q2b = DefaultStateType("2'"); - DefaultStateType q0b = DefaultStateType("0'"); - DefaultStateType q0102 = DefaultStateType("q0102"); - DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); +TEST_CASE ( "Automata Concatenation", "[unit][algo][automaton][transform]" ) { + SECTION ( "NFA/DFA" ) { + // based on Melichar, 2.79 - automaton::DFA<> m1(q1a); - automaton::DFA<> m2(q1b); - automaton::NFA < > m3(q1a); + DefaultStateType q1a = DefaultStateType("1"); + DefaultStateType q2a = DefaultStateType("2"); + DefaultStateType q0a = DefaultStateType("0"); + DefaultStateType q1b = DefaultStateType("1'"); + DefaultStateType q2b = DefaultStateType("2'"); + DefaultStateType q0b = DefaultStateType("0'"); + DefaultStateType q0102 = DefaultStateType("q0102"); + DefaultSymbolType a(DefaultSymbolType('a')), b(DefaultSymbolType('b')); - m1.setInputAlphabet({a, b}); - m1.setStates({q1a, q2a, q0a}); - m1.addTransition(q1a, a, q2a); - m1.addTransition(q1a, b, q0a); - m1.addTransition(q2a, a, q2a); - m1.addTransition(q2a, b, q0a); - m1.addTransition(q0a, a, q0a); - m1.addTransition(q0a, b, q0a); - m1.addFinalState(q2a); + automaton::DFA<> m1(q1a); + automaton::DFA<> m2(q1b); + automaton::NFA < > m3(q1a); - m2.setInputAlphabet({a, b}); - m2.setStates({q1b, q2b}); - m2.addTransition(q1b, b, q2b); - m2.addTransition(q2b, b, q2b); - m2.addFinalState(q2b); + m1.setInputAlphabet({a, b}); + m1.setStates({q1a, q2a, q0a}); + m1.addTransition(q1a, a, q2a); + m1.addTransition(q1a, b, q0a); + m1.addTransition(q2a, a, q2a); + m1.addTransition(q2a, b, q0a); + m1.addTransition(q0a, a, q0a); + m1.addTransition(q0a, b, q0a); + m1.addFinalState(q2a); - m3.setInputAlphabet({a, b}); - m3.setStates({q1a, q1b, q2a, q2b, q0a, q0b, q0102}); - m3.addTransition(q1a, a, q2a); - m3.addTransition(q1a, a, q1b); - m3.addTransition(q1a, b, q0a); - m3.addTransition(q2a, a, q2a); - m3.addTransition(q2a, a, q1b); - m3.addTransition(q2a, b, q0a); - m3.addTransition(q0a, a, q0a); - m3.addTransition(q0a, b, q0a); - m3.addTransition(q1b, a, q0b); - m3.addTransition(q1b, b, q2b); - m3.addTransition(q2b, a, q0b); - m3.addTransition(q2b, b, q2b); - m3.addTransition(q0b, a, q0b); - m3.addTransition(q0b, b, q0b); - m3.setFinalStates({q2b}); + m2.setInputAlphabet({a, b}); + m2.setStates({q1b, q2b}); + m2.addTransition(q1b, b, q2b); + m2.addTransition(q2b, b, q2b); + m2.addFinalState(q2b); - auto u11 = automaton::transform::AutomataConcatenationEpsilonTransition::concatenation(automaton::NFA<>(automaton::DFA<>(m1)), automaton::NFA < > (m2)); - auto u12 = automaton::transform::AutomataConcatenationEpsilonTransition::concatenation(automaton::DFA<>(m1), automaton::DFA<>(m2)); - auto u21 = automaton::transform::AutomataConcatenation::concatenation(automaton::NFA<>(automaton::DFA<>(m1)), automaton::NFA < > (m2)); - auto u22 = automaton::transform::AutomataConcatenation::concatenation(automaton::DFA<>(m1), automaton::DFA<>(m2)); + m3.setInputAlphabet({a, b}); + m3.setStates({q1a, q1b, q2a, q2b, q0a, q0b, q0102}); + m3.addTransition(q1a, a, q2a); + m3.addTransition(q1a, a, q1b); + m3.addTransition(q1a, b, q0a); + m3.addTransition(q2a, a, q2a); + m3.addTransition(q2a, a, q1b); + m3.addTransition(q2a, b, q0a); + m3.addTransition(q0a, a, q0a); + m3.addTransition(q0a, b, q0a); + m3.addTransition(q1b, a, q0b); + m3.addTransition(q1b, b, q2b); + m3.addTransition(q2b, a, q0b); + m3.addTransition(q2b, b, q2b); + m3.addTransition(q0b, a, q0b); + m3.addTransition(q0b, b, q0b); + m3.setFinalStates({q2b}); - automaton::DFA < DefaultSymbolType, unsigned > umdfa (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(m3))))); - automaton::DFA < DefaultSymbolType, unsigned > umdfa11(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u11))))); - automaton::DFA < DefaultSymbolType, unsigned > umdfa12(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u12))))); - automaton::DFA < DefaultSymbolType, unsigned > umdfa21(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u21))))); - automaton::DFA < DefaultSymbolType, unsigned > umdfa22(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u22))))); + auto u11 = automaton::transform::AutomataConcatenationEpsilonTransition::concatenation(automaton::NFA<>(automaton::DFA<>(m1)), automaton::NFA < > (m2)); + auto u12 = automaton::transform::AutomataConcatenationEpsilonTransition::concatenation(automaton::DFA<>(m1), automaton::DFA<>(m2)); + auto u21 = automaton::transform::AutomataConcatenation::concatenation(automaton::NFA<>(automaton::DFA<>(m1)), automaton::NFA < > (m2)); + auto u22 = automaton::transform::AutomataConcatenation::concatenation(automaton::DFA<>(m1), automaton::DFA<>(m2)); - CPPUNIT_ASSERT(umdfa11 == umdfa); - CPPUNIT_ASSERT(umdfa12 == umdfa); - CPPUNIT_ASSERT(umdfa21 == umdfa); - CPPUNIT_ASSERT(umdfa22 == umdfa); + automaton::DFA < DefaultSymbolType, unsigned > umdfa (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(m3))))); + automaton::DFA < DefaultSymbolType, unsigned > umdfa11(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u11))))); + automaton::DFA < DefaultSymbolType, unsigned > umdfa12(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u12))))); + automaton::DFA < DefaultSymbolType, unsigned > umdfa21(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u21))))); + automaton::DFA < DefaultSymbolType, unsigned > umdfa22(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u22))))); + CHECK(umdfa11 == umdfa); + CHECK(umdfa12 == umdfa); + CHECK(umdfa21 == umdfa); + CHECK(umdfa22 == umdfa); + } } diff --git a/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.h b/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.h deleted file mode 100644 index aa7dbecb20..0000000000 --- a/alib2algo/test-src/automaton/transform/AutomataConcatenationTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef AUTOMATA_CONCAT_TEST_H_ -#define AUTOMATA_CONCAT_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class AutomataConcatenationTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( AutomataConcatenationTest ); - CPPUNIT_TEST( testAutomataConcatenation ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testAutomataConcatenation(); -}; - -#endif /* AUTOMATA_CONCAT_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/transform/AutomataUnionTest.cpp b/alib2algo/test-src/automaton/transform/AutomataUnionTest.cpp index ee38f8eab0..6e3a23fe21 100644 --- a/alib2algo/test-src/automaton/transform/AutomataUnionTest.cpp +++ b/alib2algo/test-src/automaton/transform/AutomataUnionTest.cpp @@ -1,5 +1,6 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "AutomataUnionTest.h" #include "automaton/transform/AutomataUnionCartesianProduct.h" #include "automaton/transform/AutomataUnionEpsilonTransition.h" @@ -12,16 +13,8 @@ #include <exception/CommonException.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( AutomataUnionTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( AutomataUnionTest ); - -void AutomataUnionTest::setUp() { -} - -void AutomataUnionTest::tearDown() { -} - -void AutomataUnionTest::testAutomataUnion() { +TEST_CASE ( "Automata Union", "[unit][algo][automaton][transform]" ) { + SECTION ( "NFA/DFA" ) { // based on Melichar, 2.72 DefaultStateType q1a = DefaultStateType("1"); @@ -69,15 +62,15 @@ void AutomataUnionTest::testAutomataUnion() { m3.setFinalStates({q20, q02}); auto u1 = automaton::transform::AutomataUnionEpsilonTransition::unification(m1, m2); - CPPUNIT_ASSERT_THROW(automaton::transform::AutomataUnionCartesianProduct::unification(m1, m2), exception::CommonException); - CPPUNIT_ASSERT_THROW(automaton::transform::AutomataUnionCartesianProduct::unification(automaton::NFA < > (m1), automaton::NFA < > ( m2 )), exception::CommonException); + CHECK_THROWS_AS(automaton::transform::AutomataUnionCartesianProduct::unification(m1, m2), exception::CommonException); + CHECK_THROWS_AS(automaton::transform::AutomataUnionCartesianProduct::unification(automaton::NFA < > (m1), automaton::NFA < > ( m2 )), exception::CommonException); auto u2 = automaton::transform::AutomataUnionEpsilonTransition::unification(automaton::simplify::Total::total(m1), automaton::simplify::Total::total(m2)); auto umdfa(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(m3))))); auto umdfa1(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u1))))); auto umdfa2(automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(u2))))); - CPPUNIT_ASSERT(umdfa1 == umdfa); - CPPUNIT_ASSERT(umdfa2 == umdfa); - + CHECK(umdfa1 == umdfa); + CHECK(umdfa2 == umdfa); +} } diff --git a/alib2algo/test-src/automaton/transform/AutomataUnionTest.h b/alib2algo/test-src/automaton/transform/AutomataUnionTest.h deleted file mode 100644 index d45ef404d8..0000000000 --- a/alib2algo/test-src/automaton/transform/AutomataUnionTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef AUTOMATA_UNION_TEST_H_ -#define AUTOMATA_UNION_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class AutomataUnionTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( AutomataUnionTest ); - CPPUNIT_TEST( testAutomataUnion ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testAutomataUnion(); -}; - -#endif /* AUTOMATA_UNION_TEST_H_ */ diff --git a/alib2algo/test-src/automaton/transform/AutomatonIterationTest.cpp b/alib2algo/test-src/automaton/transform/AutomatonIterationTest.cpp index 31e6d3d326..b02ab93fe0 100644 --- a/alib2algo/test-src/automaton/transform/AutomatonIterationTest.cpp +++ b/alib2algo/test-src/automaton/transform/AutomatonIterationTest.cpp @@ -1,5 +1,6 @@ +#include <catch2/catch.hpp> + #include <alib/list> -#include "AutomatonIterationTest.h" #include "automaton/transform/AutomatonIteration.h" #include "automaton/transform/AutomatonIterationEpsilonTransition.h" @@ -11,54 +12,46 @@ #include "automaton/simplify/Total.h" #include "automaton/determinize/Determinize.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( AutomatonIterationTest, "automaton" ); -CPPUNIT_TEST_SUITE_REGISTRATION( AutomatonIterationTest ); - -void AutomatonIterationTest::setUp() { -} - -void AutomatonIterationTest::tearDown() { -} - -void AutomatonIterationTest::testAutomatonIteration() { - - // Melichar 2.83 - DefaultStateType q0 = DefaultStateType(0); - DefaultStateType q1 = DefaultStateType(1); - DefaultStateType q2 = DefaultStateType(2); - DefaultStateType q3 = DefaultStateType(3); - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - automaton::DFA < > m1(q1); - m1.setStates({q1, q2, q3}); - m1.addFinalState(q3); - m1.setInputAlphabet({a, b}); - m1.addTransition(q1, a, q2); - m1.addTransition(q2, b, q2); - m1.addTransition(q2, a, q3); - m1.addTransition(q3, a, q1); - - automaton::EpsilonNFA < > res(q0); - res.setStates({q0, q1, q2, q3}); - res.setInputAlphabet({a, b}); - res.setFinalStates({q0, q3}); - - res.addTransition(q1, a, q2); - res.addTransition(q2, b, q2); - res.addTransition(q2, a, q3); - res.addTransition(q3, a, q1); - - res.addTransition(q0, q1); - res.addTransition(q3, q1); - - auto i2 = automaton::transform::AutomatonIterationEpsilonTransition::iteration(m1); - auto i1 = automaton::transform::AutomatonIteration::iteration(m1); - - auto mdfa1 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(i1))))); - auto mdfa2 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(i2))))); - auto mdfa3 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(res))))); - - CPPUNIT_ASSERT(mdfa1 == mdfa2); - CPPUNIT_ASSERT(mdfa1 == mdfa3); +TEST_CASE ( "Automata Iteration", "[unit][algo][automaton][transform]" ) { + SECTION ( "NFA/DFA" ) { + // Melichar 2.83 + DefaultStateType q0 = DefaultStateType(0); + DefaultStateType q1 = DefaultStateType(1); + DefaultStateType q2 = DefaultStateType(2); + DefaultStateType q3 = DefaultStateType(3); + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + automaton::DFA < > m1(q1); + m1.setStates({q1, q2, q3}); + m1.addFinalState(q3); + m1.setInputAlphabet({a, b}); + m1.addTransition(q1, a, q2); + m1.addTransition(q2, b, q2); + m1.addTransition(q2, a, q3); + m1.addTransition(q3, a, q1); + + automaton::EpsilonNFA < > res(q0); + res.setStates({q0, q1, q2, q3}); + res.setInputAlphabet({a, b}); + res.setFinalStates({q0, q3}); + + res.addTransition(q1, a, q2); + res.addTransition(q2, b, q2); + res.addTransition(q2, a, q3); + res.addTransition(q3, a, q1); + + res.addTransition(q0, q1); + res.addTransition(q3, q1); + + auto i2 = automaton::transform::AutomatonIterationEpsilonTransition::iteration(m1); + auto i1 = automaton::transform::AutomatonIteration::iteration(m1); + + auto mdfa1 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(i1))))); + auto mdfa2 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(i2))))); + auto mdfa3 (automaton::simplify::Normalize::normalize(automaton::simplify::Trim::trim(automaton::simplify::MinimizeBrzozowski::minimize(automaton::simplify::EpsilonRemoverIncoming::remove(res))))); + + CHECK(mdfa1 == mdfa2); + CHECK(mdfa1 == mdfa3); + } } diff --git a/alib2algo/test-src/automaton/transform/AutomatonIterationTest.h b/alib2algo/test-src/automaton/transform/AutomatonIterationTest.h deleted file mode 100644 index 28119050ac..0000000000 --- a/alib2algo/test-src/automaton/transform/AutomatonIterationTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef AUTOMATA_ITER_TEST_H_ -#define AUTOMATA_ITER_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class AutomatonIterationTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( AutomatonIterationTest ); - CPPUNIT_TEST( testAutomatonIteration ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testAutomatonIteration(); -}; - -#endif /* AUTOMATA_ITER_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.cpp b/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.cpp index cb6b6bcaa1..e8788ae261 100644 --- a/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.cpp +++ b/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.cpp @@ -1,4 +1,4 @@ -#include "GrammarCFGtoPDATest.h" +#include <catch2/catch.hpp> #include <alphabet/BottomOfTheStackSymbol.h> #include <grammar/ContextFree/CFG.h> @@ -11,18 +11,8 @@ #include <label/InitialStateLabel.h> #include <label/FinalStateLabel.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarCFGtoPDATest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarCFGtoPDATest ); - -void GrammarCFGtoPDATest::setUp() { -} - -void GrammarCFGtoPDATest::tearDown() { -} - -void GrammarCFGtoPDATest::testTopDown() -{ - { +TEST_CASE ( "CFG to PDA", "[unit][algo][grammar][convert]" ) { + SECTION ( "Top down" ) { std::string nE = "E"; std::string nT = "T"; std::string nF = "F"; @@ -59,13 +49,10 @@ void GrammarCFGtoPDATest::testTopDown() for ( char symbol : pda.getInputAlphabet ( ) ) pda.addTransition ( q, symbol, ext::vector<ext::variant < char, std::string >>{symbol}, q, ext::vector<ext::variant < char, std::string >>{}); - CPPUNIT_ASSERT(pda == grammar::convert::ToAutomaton::convert(grammar)); + CHECK (pda == grammar::convert::ToAutomaton::convert(grammar)); } -} -void GrammarCFGtoPDATest::testBottomUp() -{ - { + SECTION ( "Bottom up" ) { DefaultSymbolType nE = DefaultSymbolType('E'); DefaultSymbolType nT = DefaultSymbolType('T'); DefaultSymbolType nF = DefaultSymbolType('F'); @@ -109,6 +96,6 @@ void GrammarCFGtoPDATest::testBottomUp() pda.addTransition(q, ext::vector < ext::variant < DefaultSymbolType, DefaultSymbolType > >{bots, nE}, r, ext::vector < ext::variant < DefaultSymbolType, DefaultSymbolType > >{}); - CPPUNIT_ASSERT(pda == grammar::convert::ToAutomatonBottomUp::convert(grammar)); + CHECK (pda == grammar::convert::ToAutomatonBottomUp::convert(grammar)); } } diff --git a/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.h b/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.h deleted file mode 100644 index 21164e6062..0000000000 --- a/alib2algo/test-src/grammar/convert/GrammarCFGtoPDATest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef GRAMMAR_CFG_TO_PDA_TEST_H_ -#define GRAMMAR_CFG_TO_PDA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarCFGtoPDATest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarCFGtoPDATest ); - CPPUNIT_TEST( testBottomUp ); - CPPUNIT_TEST( testTopDown ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testBottomUp(); - void testTopDown(); -}; - -#endif /* GRAMMAR_CFG_TO_PDA_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/convert/rg2rgTest.cpp b/alib2algo/test-src/grammar/convert/rg2rgTest.cpp new file mode 100644 index 0000000000..aaa83a5605 --- /dev/null +++ b/alib2algo/test-src/grammar/convert/rg2rgTest.cpp @@ -0,0 +1,69 @@ +#include <catch2/catch.hpp> + +#include "grammar/convert/ToGrammarLeftRG.h" +#include "grammar/convert/ToGrammarRightRG.h" + +TEST_CASE ( "Left <-> Right Regular Grammar", "[unit][algo][grammar][convert]" ) { + SECTION ( "Right to left" ) { + grammar::RightRG < > rrGrammar(DefaultSymbolType(1)); + + rrGrammar.addNonterminalSymbol(DefaultSymbolType(1)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); + rrGrammar.addTerminalSymbol(DefaultSymbolType("a")); + rrGrammar.addTerminalSymbol(DefaultSymbolType("b")); + + rrGrammar.addRule(DefaultSymbolType(1), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); + rrGrammar.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); + rrGrammar.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); + + grammar::LeftRG < > lrGrammar = grammar::convert::ToGrammarLeftRG::convert(rrGrammar); + + DefaultSymbolType four ( object::AnyObject < int > ( 1, 1 ) ); + grammar::LeftRG < > lrGrammarRef ( four ); + + lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(1)); + lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(2)); + lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(3)); + lrGrammarRef.addTerminalSymbol(DefaultSymbolType("a")); + lrGrammarRef.addTerminalSymbol(DefaultSymbolType("b")); + + lrGrammarRef.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType(1), DefaultSymbolType("a"))); + lrGrammarRef.addRule(DefaultSymbolType(2), DefaultSymbolType("a")); + lrGrammarRef.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType(2), DefaultSymbolType("b"))); + lrGrammarRef.addRule(four, ext::make_pair(DefaultSymbolType(3), DefaultSymbolType("a"))); + + CHECK(lrGrammarRef == lrGrammar); + } + SECTION ( "Left to right" ) { + grammar::LeftRG < > lrGrammar(DefaultSymbolType(4)); + + lrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); + lrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); + lrGrammar.addNonterminalSymbol(DefaultSymbolType(4)); + lrGrammar.addTerminalSymbol(DefaultSymbolType("a")); + lrGrammar.addTerminalSymbol(DefaultSymbolType("b")); + + lrGrammar.addRule(DefaultSymbolType(2), DefaultSymbolType("a")); + lrGrammar.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType(2), DefaultSymbolType("b"))); + lrGrammar.addRule(DefaultSymbolType(4), ext::make_pair(DefaultSymbolType(3), DefaultSymbolType("a"))); + + grammar::RightRG < > rrGrammar = grammar::convert::ToGrammarRightRG::convert(lrGrammar); + + DefaultSymbolType five ( object::AnyObject < int > ( 4, 1 ) ); + grammar::RightRG < > rrGrammarRef ( five ); + + rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(2)); + rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(3)); + rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(4)); + rrGrammarRef.addTerminalSymbol(DefaultSymbolType("a")); + rrGrammarRef.addTerminalSymbol(DefaultSymbolType("b")); + + rrGrammarRef.addRule(five, ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); + rrGrammarRef.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); + rrGrammarRef.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); + rrGrammarRef.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(4))); + + CHECK(rrGrammarRef == rrGrammar); + } +} diff --git a/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.cpp b/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.cpp index 76ac22a25b..5f00c06f64 100644 --- a/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.cpp +++ b/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.cpp @@ -1,4 +1,4 @@ -#include "GrammarGenerateUpToLength.h" +#include <catch2/catch.hpp> #include <grammar/generate/GenerateUpToLength.h> @@ -8,16 +8,7 @@ #include <factory/StringDataFactory.hpp> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarGenerateUpToLength, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarGenerateUpToLength ); - -void GrammarGenerateUpToLength::setUp() { -} - -void GrammarGenerateUpToLength::tearDown() { -} - -unsigned countStrings ( const ext::trie < DefaultSymbolType, bool > & node ) { +static unsigned countStrings ( const ext::trie < DefaultSymbolType, bool > & node ) { unsigned res = node.getData ( ); for ( const auto & child : node.getChildren ( ) ) @@ -26,179 +17,184 @@ unsigned countStrings ( const ext::trie < DefaultSymbolType, bool > & node ) { return res; } -void GrammarGenerateUpToLength::testGenerate1() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - grammar1.setGeneratesEpsilon(false); - - ext::set<string::LinearString < >> strings; - - ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 5); - - generated.nicePrint ( std::cout ); - std::cout << std::endl; - - for(const string::LinearString < > & str : strings) { - bool flag = true; - ext::trie < DefaultSymbolType, bool > * node = & generated; - for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { - auto iter = node->getChildren ( ).find ( symbol ); - if ( iter == node->getChildren ( ).end ( ) ) { - flag = false; - break; +TEST_CASE ( "Generate Up To", "[unit][algo][grammar][generate]" ) { + SECTION ( "Test eps-free CFG" ) { + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + grammar1.setGeneratesEpsilon(false); + + ext::set<string::LinearString < >> strings; + + ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 5); + + std::ostringstream oss; + generated.nicePrint ( oss ); + CAPTURE ( oss.str ( ) ); + + for(const string::LinearString < > & str : strings) { + bool flag = true; + ext::trie < DefaultSymbolType, bool > * node = & generated; + for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { + auto iter = node->getChildren ( ).find ( symbol ); + if ( iter == node->getChildren ( ).end ( ) ) { + flag = false; + break; + } + node = & iter->second; + } + + CAPTURE ( factory::StringDataFactory::toString ( str ) ); + CHECK ( ( flag && node->getData ( ) == true ) ); } - node = & iter->second; - } - - CPPUNIT_ASSERT ( flag && node->getData ( ) == true ); - std::cout << factory::StringDataFactory::toString ( str ) << std::endl; - } - - CPPUNIT_ASSERT(strings.size ( ) == countStrings ( generated ) ); -} -void GrammarGenerateUpToLength::testGenerate2() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A, D}); - grammar1.addRule(S, {A}); - grammar1.addRule(S, {D}); - grammar1.addRule(A, {a, A, d}); - grammar1.addRule(A, {a, d}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(A, {B}); - grammar1.addRule(A, {C}); - grammar1.addRule(B, {b, B, c}); - grammar1.addRule(B, {b, c}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {c}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {d}); - grammar1.setGeneratesEpsilon(true); - - ext::set<string::LinearString < >> strings; - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, c})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, c})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, c, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, d})); - - ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 3); - - generated.nicePrint ( std::cout ); - std::cout << std::endl; - - for(const string::LinearString < > & str : strings) { - bool flag = true; - ext::trie < DefaultSymbolType, bool > * node = & generated; - for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { - auto iter = node->getChildren ( ).find ( symbol ); - if ( iter == node->getChildren ( ).end ( ) ) { - flag = false; - break; - } - node = & iter->second; + CHECK (strings.size ( ) == countStrings ( generated ) ); } - - CPPUNIT_ASSERT ( flag && node->getData ( ) == true ); - std::cout << factory::StringDataFactory::toString ( str ) << std::endl; - } - - CPPUNIT_ASSERT(strings.size ( ) == countStrings ( generated ) ); -} - -void GrammarGenerateUpToLength::testGenerate3() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A, D}); - grammar1.addRule(S, {D}); - grammar1.addRule(A, {a, A, d}); - grammar1.addRule(A, {a, d}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(A, {B}); - grammar1.addRule(A, {C}); - grammar1.addRule(B, {b, B, c}); - grammar1.addRule(B, {b, c}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {c}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {d}); - - ext::set<string::LinearString < >> strings; - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d, d})); - strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, d})); - - ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 3); - - generated.nicePrint ( std::cout ); - std::cout << std::endl; - - for(const string::LinearString < > & str : strings) { - bool flag = true; - ext::trie < DefaultSymbolType, bool > * node = & generated; - for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { - auto iter = node->getChildren ( ).find ( symbol ); - if ( iter == node->getChildren ( ).end ( ) ) { - flag = false; - break; + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A, D}); + grammar1.addRule(S, {A}); + grammar1.addRule(S, {D}); + grammar1.addRule(A, {a, A, d}); + grammar1.addRule(A, {a, d}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(A, {B}); + grammar1.addRule(A, {C}); + grammar1.addRule(B, {b, B, c}); + grammar1.addRule(B, {b, c}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {c}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {d}); + grammar1.setGeneratesEpsilon(true); + + ext::set<string::LinearString < >> strings; + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, c})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, c})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, c, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, d})); + + ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 3); + + std::ostringstream oss; + generated.nicePrint ( oss ); + CAPTURE ( oss.str ( ) ); + + for(const string::LinearString < > & str : strings) { + bool flag = true; + ext::trie < DefaultSymbolType, bool > * node = & generated; + for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { + auto iter = node->getChildren ( ).find ( symbol ); + if ( iter == node->getChildren ( ).end ( ) ) { + flag = false; + break; + } + node = & iter->second; + } + + CAPTURE ( factory::StringDataFactory::toString ( str ) ); + CHECK ( ( flag && node->getData ( ) == true ) ); } - node = & iter->second; + + CHECK (strings.size ( ) == countStrings ( generated ) ); } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A, D}); + grammar1.addRule(S, {D}); + grammar1.addRule(A, {a, A, d}); + grammar1.addRule(A, {a, d}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(A, {B}); + grammar1.addRule(A, {C}); + grammar1.addRule(B, {b, B, c}); + grammar1.addRule(B, {b, c}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {c}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {d}); + + ext::set<string::LinearString < >> strings; + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{d, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{a, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, c, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{c, d, d})); + strings.insert(string::LinearString < >(ext::vector<DefaultSymbolType>{b, c, d})); + + ext::trie < DefaultSymbolType, bool > generated = grammar::generate::GenerateUpToLength::generate(grammar1, 3); + + std::ostringstream oss; + generated.nicePrint ( oss ); + CAPTURE ( oss.str ( ) ); + + for(const string::LinearString < > & str : strings) { + bool flag = true; + ext::trie < DefaultSymbolType, bool > * node = & generated; + for ( const DefaultSymbolType & symbol : str.getContent ( ) ) { + auto iter = node->getChildren ( ).find ( symbol ); + if ( iter == node->getChildren ( ).end ( ) ) { + flag = false; + break; + } + node = & iter->second; + } + + CAPTURE ( factory::StringDataFactory::toString ( str ) ); + CHECK ( ( flag && node->getData ( ) == true ) ); + } - CPPUNIT_ASSERT ( flag && node->getData ( ) == true ); - std::cout << factory::StringDataFactory::toString ( str ) << std::endl; + CHECK(strings.size ( ) == countStrings ( generated ) ); + } } - - CPPUNIT_ASSERT(strings.size ( ) == countStrings ( generated ) ); } diff --git a/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.h b/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.h deleted file mode 100644 index bce267fbef..0000000000 --- a/alib2algo/test-src/grammar/generate/GrammarGenerateUpToLength.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef GRAMMAR_GENERATE_UP_TO_LENGTH_TEST_H_ -#define GRAMMAR_GENERATE_UP_TO_LENGTH_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarGenerateUpToLength : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarGenerateUpToLength ); - CPPUNIT_TEST( testGenerate1 ); - CPPUNIT_TEST( testGenerate2 ); - CPPUNIT_TEST( testGenerate3 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testGenerate1(); - void testGenerate2(); - void testGenerate3(); -}; - -#endif /* GRAMMAR_GENERATE_UP_TO_LENGTH_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.cpp b/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.cpp index 0c8478a7cd..09ed469675 100644 --- a/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.cpp +++ b/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.cpp @@ -1,4 +1,4 @@ -#include "GrammarPropertiesTest.h" +#include <catch2/catch.hpp> #include <grammar/Grammar.h> #include <grammar/ContextFree/CFG.h> @@ -8,146 +8,138 @@ #include "grammar/properties/NonterminalUnitRuleCycle.h" #include "grammar/properties/RecursiveNonterminal.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarPropertiesTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarPropertiesTest ); - -void GrammarPropertiesTest::setUp() { -} - -void GrammarPropertiesTest::tearDown() { -} - -void GrammarPropertiesTest::testNullable() { - DefaultSymbolType X = DefaultSymbolType('X'); - DefaultSymbolType Y = DefaultSymbolType('Y'); - DefaultSymbolType Z = DefaultSymbolType('Z'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::CFG < > grammar(X); - grammar.setTerminalAlphabet({d}); - grammar.setNonterminalAlphabet({{X, Y, Z}}); - grammar.setInitialSymbol(X); - - grammar.addRule(X, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); - grammar.addRule(X, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ Y }); - grammar.addRule(Y, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); - grammar.addRule(Y, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ }); - grammar.addRule(Z, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); - grammar.addRule(Z, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ X, Y, Z }); - - ext::set<DefaultSymbolType> res = {X, Y}; - CPPUNIT_ASSERT(res == grammar::properties::NullableNonterminals::getNullableNonterminals(grammar)); -} - -void GrammarPropertiesTest::testUnitRules() { - DefaultSymbolType S = DefaultSymbolType('S'); - DefaultSymbolType A = DefaultSymbolType('A'); - DefaultSymbolType B = DefaultSymbolType('B'); - DefaultSymbolType C = DefaultSymbolType('C'); - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::LeftLG < > llg(S); - llg.setTerminalAlphabet({a, b}); - llg.setNonterminalAlphabet({S, A, B, C}); - llg.setInitialSymbol(S); - - llg.addRule(S, ext::make_pair(A, ext::vector<DefaultSymbolType>{})); - llg.addRule(S, ext::make_pair(B, ext::vector<DefaultSymbolType>{})); - llg.addRule(A, ext::make_pair(A, ext::vector<DefaultSymbolType>{a})); - llg.addRule(A, ext::make_pair(B, ext::vector<DefaultSymbolType>{})); - llg.addRule(A, ext::make_pair(C, ext::vector<DefaultSymbolType>{})); - llg.addRule(B, ext::make_pair(B, ext::vector<DefaultSymbolType>{b, a})); - llg.addRule(B, ext::make_pair(C, ext::vector<DefaultSymbolType>{b})); - llg.addRule(C, {b}); - llg.addRule(C, ext::make_pair(C, ext::vector<DefaultSymbolType>{a})); - - ext::set<DefaultSymbolType> N_S = {S, A, B, C}; - ext::set<DefaultSymbolType> N_A = {A, B, C}; - ext::set<DefaultSymbolType> N_B = {B}; - ext::set<DefaultSymbolType> N_C = {C}; - - CPPUNIT_ASSERT(N_S == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, S)); - CPPUNIT_ASSERT(N_A == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, A)); - CPPUNIT_ASSERT(N_B == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, B)); - CPPUNIT_ASSERT(N_C == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, C)); -} - -void GrammarPropertiesTest::testRecursive() { - { - DefaultSymbolType A = DefaultSymbolType('A'); - DefaultSymbolType B = DefaultSymbolType('B'); - DefaultSymbolType C = DefaultSymbolType('C'); - DefaultSymbolType D = DefaultSymbolType('D'); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::CFG < > cfg(A); - cfg.setTerminalAlphabet({a, b}); - cfg.setNonterminalAlphabet({A, B, C, D}); - cfg.setInitialSymbol(A); - - cfg.addRule(A, {B}); - cfg.addRule(B, {C}); - cfg.addRule(C, {D}); - cfg.addRule(D, {A}); - cfg.addRule(D, {}); - - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); +TEST_CASE ( "Grammar properties", "[unit][algo][grammar][properties]" ) { + SECTION ( "Test Nullable" ) { + DefaultSymbolType X = DefaultSymbolType('X'); + DefaultSymbolType Y = DefaultSymbolType('Y'); + DefaultSymbolType Z = DefaultSymbolType('Z'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::CFG < > grammar(X); + grammar.setTerminalAlphabet({d}); + grammar.setNonterminalAlphabet({{X, Y, Z}}); + grammar.setInitialSymbol(X); + + grammar.addRule(X, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); + grammar.addRule(X, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ Y }); + grammar.addRule(Y, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); + grammar.addRule(Y, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ }); + grammar.addRule(Z, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ d }); + grammar.addRule(Z, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{ X, Y, Z }); + + ext::set<DefaultSymbolType> res = {X, Y}; + CHECK(res == grammar::properties::NullableNonterminals::getNullableNonterminals(grammar)); } - { + SECTION ( "Test Unit rules" ) { + DefaultSymbolType S = DefaultSymbolType('S'); DefaultSymbolType A = DefaultSymbolType('A'); DefaultSymbolType B = DefaultSymbolType('B'); DefaultSymbolType C = DefaultSymbolType('C'); - DefaultSymbolType D = DefaultSymbolType('D'); - DefaultSymbolType a = DefaultSymbolType('a'); DefaultSymbolType b = DefaultSymbolType('b'); - grammar::CFG < > cfg(A); - cfg.setTerminalAlphabet({a, b}); - cfg.setNonterminalAlphabet({A, B, C, D}); - cfg.setInitialSymbol(A); - - cfg.addRule(A, {B}); - cfg.addRule(B, {C}); - cfg.addRule(C, {D}); - cfg.addRule(D, {B}); - cfg.addRule(D, {}); - - CPPUNIT_ASSERT(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); + grammar::LeftLG < > llg(S); + llg.setTerminalAlphabet({a, b}); + llg.setNonterminalAlphabet({S, A, B, C}); + llg.setInitialSymbol(S); + + llg.addRule(S, ext::make_pair(A, ext::vector<DefaultSymbolType>{})); + llg.addRule(S, ext::make_pair(B, ext::vector<DefaultSymbolType>{})); + llg.addRule(A, ext::make_pair(A, ext::vector<DefaultSymbolType>{a})); + llg.addRule(A, ext::make_pair(B, ext::vector<DefaultSymbolType>{})); + llg.addRule(A, ext::make_pair(C, ext::vector<DefaultSymbolType>{})); + llg.addRule(B, ext::make_pair(B, ext::vector<DefaultSymbolType>{b, a})); + llg.addRule(B, ext::make_pair(C, ext::vector<DefaultSymbolType>{b})); + llg.addRule(C, {b}); + llg.addRule(C, ext::make_pair(C, ext::vector<DefaultSymbolType>{a})); + + ext::set<DefaultSymbolType> N_S = {S, A, B, C}; + ext::set<DefaultSymbolType> N_A = {A, B, C}; + ext::set<DefaultSymbolType> N_B = {B}; + ext::set<DefaultSymbolType> N_C = {C}; + + CHECK(N_S == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, S)); + CHECK(N_A == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, A)); + CHECK(N_B == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, B)); + CHECK(N_C == grammar::properties::NonterminalUnitRuleCycle::getNonterminalUnitRuleCycle(llg, C)); } - { - DefaultSymbolType A = DefaultSymbolType('A'); - DefaultSymbolType B = DefaultSymbolType('B'); - DefaultSymbolType C = DefaultSymbolType('C'); - DefaultSymbolType D = DefaultSymbolType('D'); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - grammar::CFG < > cfg(A); - cfg.setTerminalAlphabet({a, b}); - cfg.setNonterminalAlphabet({A, B, C, D}); - cfg.setInitialSymbol(A); - - cfg.addRule(A, {B}); - cfg.addRule(B, {C, D, A}); - cfg.addRule(C, {a}); - cfg.addRule(C, {}); - cfg.addRule(D, {b}); - cfg.addRule(D, {}); - - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); - CPPUNIT_ASSERT(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); - CPPUNIT_ASSERT(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); - CPPUNIT_ASSERT(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); + SECTION ( "Test recursive nonterminals" ) { + { + DefaultSymbolType A = DefaultSymbolType('A'); + DefaultSymbolType B = DefaultSymbolType('B'); + DefaultSymbolType C = DefaultSymbolType('C'); + DefaultSymbolType D = DefaultSymbolType('D'); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::CFG < > cfg(A); + cfg.setTerminalAlphabet({a, b}); + cfg.setNonterminalAlphabet({A, B, C, D}); + cfg.setInitialSymbol(A); + + cfg.addRule(A, {B}); + cfg.addRule(B, {C}); + cfg.addRule(C, {D}); + cfg.addRule(D, {A}); + cfg.addRule(D, {}); + + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); + } + { + DefaultSymbolType A = DefaultSymbolType('A'); + DefaultSymbolType B = DefaultSymbolType('B'); + DefaultSymbolType C = DefaultSymbolType('C'); + DefaultSymbolType D = DefaultSymbolType('D'); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::CFG < > cfg(A); + cfg.setTerminalAlphabet({a, b}); + cfg.setNonterminalAlphabet({A, B, C, D}); + cfg.setInitialSymbol(A); + + cfg.addRule(A, {B}); + cfg.addRule(B, {C}); + cfg.addRule(C, {D}); + cfg.addRule(D, {B}); + cfg.addRule(D, {}); + + CHECK(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); + } + { + DefaultSymbolType A = DefaultSymbolType('A'); + DefaultSymbolType B = DefaultSymbolType('B'); + DefaultSymbolType C = DefaultSymbolType('C'); + DefaultSymbolType D = DefaultSymbolType('D'); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::CFG < > cfg(A); + cfg.setTerminalAlphabet({a, b}); + cfg.setNonterminalAlphabet({A, B, C, D}); + cfg.setInitialSymbol(A); + + cfg.addRule(A, {B}); + cfg.addRule(B, {C, D, A}); + cfg.addRule(C, {a}); + cfg.addRule(C, {}); + cfg.addRule(D, {b}); + cfg.addRule(D, {}); + + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, A)); + CHECK(grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, B)); + CHECK(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, C)); + CHECK(!grammar::properties::RecursiveNonterminal::isNonterminalRecursive(cfg, D)); + } } } diff --git a/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.h b/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.h deleted file mode 100644 index 554472f62d..0000000000 --- a/alib2algo/test-src/grammar/properties/GrammarPropertiesTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef GRAMMAR_PROPERTIES_TEST_H_ -#define GRAMMAR_PROPERTIES_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarPropertiesTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarPropertiesTest ); - CPPUNIT_TEST( testUnitRules ); - CPPUNIT_TEST( testNullable ); - CPPUNIT_TEST( testRecursive ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testUnitRules(); - void testNullable(); - void testRecursive(); -}; - -#endif /* GRAMMAR_PROPERTIES_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.cpp b/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.cpp index 4a7f343798..1dd7384dfa 100644 --- a/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.cpp +++ b/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.cpp @@ -1,134 +1,127 @@ -#include "GrammarEpsilonRemoverTest.h" +#include <catch2/catch.hpp> #include "grammar/simplify/EpsilonRemover.h" #include "grammar/ContextFree/CFG.h" #include "grammar/ContextFree/EpsilonFreeCFG.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarEpsilonRemoverTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarEpsilonRemoverTest ); - -void GrammarEpsilonRemoverTest::setUp() { -} - -void GrammarEpsilonRemoverTest::tearDown() { -} - -void GrammarEpsilonRemoverTest::testRemoveEpsilonRules1() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::CFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b}); - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarEpsilonRemoverTest::testRemoveEpsilonRules2() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::CFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A, D}); - grammar1.addRule(A, {a, A, d}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(B, {b, B, c}); - grammar1.addRule(B, {}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b, c, d}); - grammar3.addRule(S, {A, D}); - grammar3.addRule(S, {A}); - grammar3.addRule(S, {D}); - grammar3.addRule(A, {a, A, d}); - grammar3.addRule(A, {a, d}); - grammar3.addRule(A, {B, C}); - grammar3.addRule(A, {B}); - grammar3.addRule(A, {C}); - grammar3.addRule(B, {b, B, c}); - grammar3.addRule(B, {b, c}); - grammar3.addRule(C, {c, C}); - grammar3.addRule(C, {c}); - grammar3.addRule(D, {d, D}); - grammar3.addRule(D, {d}); - grammar3.setGeneratesEpsilon(true); - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarEpsilonRemoverTest::testRemoveEpsilonRules3() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::CFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A, D}); - grammar1.addRule(A, {a, A, d}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(B, {b, B, c}); - grammar1.addRule(B, {}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {d}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b, c, d}); - grammar3.addRule(S, {A, D}); - grammar3.addRule(S, {D}); - grammar3.addRule(A, {a, A, d}); - grammar3.addRule(A, {a, d}); - grammar3.addRule(A, {B, C}); - grammar3.addRule(A, {B}); - grammar3.addRule(A, {C}); - grammar3.addRule(B, {b, B, c}); - grammar3.addRule(B, {b, c}); - grammar3.addRule(C, {c, C}); - grammar3.addRule(C, {c}); - grammar3.addRule(D, {d, D}); - grammar3.addRule(D, {d}); - - CPPUNIT_ASSERT(grammar2 == grammar3); +TEST_CASE ( "Epsilon remover", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test CFG" ) { + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::CFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b}); + + CHECK (grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::CFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A, D}); + grammar1.addRule(A, {a, A, d}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(B, {b, B, c}); + grammar1.addRule(B, {}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b, c, d}); + grammar3.addRule(S, {A, D}); + grammar3.addRule(S, {A}); + grammar3.addRule(S, {D}); + grammar3.addRule(A, {a, A, d}); + grammar3.addRule(A, {a, d}); + grammar3.addRule(A, {B, C}); + grammar3.addRule(A, {B}); + grammar3.addRule(A, {C}); + grammar3.addRule(B, {b, B, c}); + grammar3.addRule(B, {b, c}); + grammar3.addRule(C, {c, C}); + grammar3.addRule(C, {c}); + grammar3.addRule(D, {d, D}); + grammar3.addRule(D, {d}); + grammar3.setGeneratesEpsilon(true); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::CFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A, D}); + grammar1.addRule(A, {a, A, d}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(B, {b, B, c}); + grammar1.addRule(B, {}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {d}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::EpsilonRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b, c, d}); + grammar3.addRule(S, {A, D}); + grammar3.addRule(S, {D}); + grammar3.addRule(A, {a, A, d}); + grammar3.addRule(A, {a, d}); + grammar3.addRule(A, {B, C}); + grammar3.addRule(A, {B}); + grammar3.addRule(A, {C}); + grammar3.addRule(B, {b, B, c}); + grammar3.addRule(B, {b, c}); + grammar3.addRule(C, {c, C}); + grammar3.addRule(C, {c}); + grammar3.addRule(D, {d, D}); + grammar3.addRule(D, {d}); + + CHECK(grammar2 == grammar3); + } + } } diff --git a/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.h b/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.h deleted file mode 100644 index b536b53c98..0000000000 --- a/alib2algo/test-src/grammar/simplify/GrammarEpsilonRemoverTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef GRAMMAR_EPSILON_REMOVER_TEST_H_ -#define GRAMMAR_EPSILON_REMOVER_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarEpsilonRemoverTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarEpsilonRemoverTest ); - CPPUNIT_TEST( testRemoveEpsilonRules1 ); - CPPUNIT_TEST( testRemoveEpsilonRules2 ); - CPPUNIT_TEST( testRemoveEpsilonRules3 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRemoveEpsilonRules1(); - void testRemoveEpsilonRules2(); - void testRemoveEpsilonRules3(); -}; - -#endif /* GRAMMAR_EPSILON_REMOVER_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.cpp b/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.cpp index eec5bb9017..ca1373c9b6 100644 --- a/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.cpp +++ b/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.cpp @@ -1,4 +1,4 @@ -#include "GrammarLeftRecursionRemoverTest.h" +#include <catch2/catch.hpp> #include "grammar/simplify/LeftRecursionRemover.h" #include "grammar/generate/GenerateUpToLength.h" @@ -12,202 +12,187 @@ #include <factory/StringDataFactory.hpp> #include <common/createUnique.hpp> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarLeftRecursionRemoverTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarLeftRecursionRemoverTest ); - -void GrammarLeftRecursionRemoverTest::setUp() { -} - -void GrammarLeftRecursionRemoverTest::tearDown() { -} - -void GrammarLeftRecursionRemoverTest::testRemoveLefRecursion1() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b}); - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarLeftRecursionRemoverTest::testRemoveLefRecursion2() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {A, a}); - grammar1.addRule(A, {A, b}); - grammar1.addRule(A, {c}); - - DefaultSymbolType Aprimed = common::createUnique(A, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - std::cout << factory::StringDataFactory::toString ( grammar1 ) << std::endl; - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, Aprimed, B, C, D}); - grammar3.setTerminalAlphabet({a, b, c}); - grammar3.addRule(S, {c, Aprimed}); - grammar3.addRule(S, {c}); - grammar3.addRule(A, {c, Aprimed}); - grammar3.addRule(A, {c}); - grammar3.addRule(Aprimed, {a, Aprimed}); - grammar3.addRule(Aprimed, {a}); - grammar3.addRule(Aprimed, {b, Aprimed}); - grammar3.addRule(Aprimed, {b}); - - std::cout << factory::StringDataFactory::toString( grammar2 ) << std::endl; - std::cout << factory::StringDataFactory::toString( grammar3 ) << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarLeftRecursionRemoverTest::testRemoveLefRecursion3() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C}); - grammar1.setTerminalAlphabet({a, b, c}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {B, a}); - grammar1.addRule(B, {A, b}); - grammar1.addRule(A, {c}); - - DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - std::cout << factory::StringDataFactory::toString ( grammar1 ) << std::endl; - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, Bprimed, C}); - grammar3.setTerminalAlphabet({a, b, c}); - grammar3.addRule(S, {c}); - grammar3.addRule(S, {c, b, Bprimed, a}); - grammar3.addRule(S, {c, b, a}); - grammar3.addRule(A, {B, a}); - grammar3.addRule(A, {c}); - grammar3.addRule(B, {c, b}); - grammar3.addRule(B, {c, b, Bprimed}); - grammar3.addRule(Bprimed, {a, b, Bprimed}); - grammar3.addRule(Bprimed, {a, b}); - - std::cout << factory::StringDataFactory::toString ( grammar2 ) << std::endl; - std::cout << factory::StringDataFactory::toString ( grammar3 ) << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarLeftRecursionRemoverTest::testRemoveLefRecursion4() { - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::EpsilonFreeCFG < > grammar1(A); - grammar1.setNonterminalAlphabet({A, B, C}); - grammar1.setTerminalAlphabet({a, b}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(A, {a}); - grammar1.addRule(B, {C, A}); - grammar1.addRule(B, {A, b}); - grammar1.addRule(C, {A, B}); - grammar1.addRule(C, {C, C}); - grammar1.addRule(C, {a}); - - DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType Cprimed = common::createUnique(C, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - std::cout << factory::StringDataFactory::toString ( grammar1 ) << std::endl; - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(A); - grammar3.setNonterminalAlphabet({A, B, Bprimed, C, Cprimed}); - grammar3.setTerminalAlphabet({a, b}); - grammar3.addRule(A, {B, C}); - grammar3.addRule(A, {a}); - grammar3.addRule(B, {C, A}); - grammar3.addRule(B, {a, b}); - grammar3.addRule(B, {C, A, Bprimed}); - grammar3.addRule(B, {a, b, Bprimed}); - grammar3.addRule(Bprimed, {C, b, Bprimed}); - grammar3.addRule(Bprimed, {C, b}); - grammar3.addRule(C, {a, b, C, B}); - grammar3.addRule(C, {a, b, Bprimed, C, B}); - grammar3.addRule(C, {a, B}); - grammar3.addRule(C, {a}); - grammar3.addRule(C, {a, b, C, B, Cprimed}); - grammar3.addRule(C, {a, b, Bprimed, C, B, Cprimed}); - grammar3.addRule(C, {a, B, Cprimed}); - grammar3.addRule(C, {a, Cprimed}); - grammar3.addRule(Cprimed, {A, C, B, Cprimed}); - grammar3.addRule(Cprimed, {A, Bprimed, C, B, Cprimed}); - grammar3.addRule(Cprimed, {C, Cprimed}); - grammar3.addRule(Cprimed, {A, C, B}); - grammar3.addRule(Cprimed, {A, Bprimed, C, B}); - grammar3.addRule(Cprimed, {C}); - - std::cout << factory::StringDataFactory::toString( grammar2 ) << std::endl; - std::cout << factory::StringDataFactory::toString( grammar3 ) << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarLeftRecursionRemoverTest::testRemoveLefRecursion5() { - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::EpsilonFreeCFG < > grammar1(A); - grammar1.setNonterminalAlphabet({A, B, C}); - grammar1.setTerminalAlphabet({a, b}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(A, {a}); - grammar1.addRule(B, {C, A}); - grammar1.addRule(B, {A, b}); - grammar1.addRule(C, {A, B}); - grammar1.addRule(C, {C, C}); - grammar1.addRule(C, {a}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); - - CPPUNIT_ASSERT(grammar::generate::GenerateUpToLength::generate(grammar1, 7) == grammar::generate::GenerateUpToLength::generate(grammar2, 7)); +TEST_CASE ( "Left recursion remover", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test eps-free CFG" ) { + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b}); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {A, a}); + grammar1.addRule(A, {A, b}); + grammar1.addRule(A, {c}); + + DefaultSymbolType Aprimed = common::createUnique(A, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, Aprimed, B, C, D}); + grammar3.setTerminalAlphabet({a, b, c}); + grammar3.addRule(S, {c, Aprimed}); + grammar3.addRule(S, {c}); + grammar3.addRule(A, {c, Aprimed}); + grammar3.addRule(A, {c}); + grammar3.addRule(Aprimed, {a, Aprimed}); + grammar3.addRule(Aprimed, {a}); + grammar3.addRule(Aprimed, {b, Aprimed}); + grammar3.addRule(Aprimed, {b}); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C}); + grammar1.setTerminalAlphabet({a, b, c}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {B, a}); + grammar1.addRule(B, {A, b}); + grammar1.addRule(A, {c}); + + DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, Bprimed, C}); + grammar3.setTerminalAlphabet({a, b, c}); + grammar3.addRule(S, {c}); + grammar3.addRule(S, {c, b, Bprimed, a}); + grammar3.addRule(S, {c, b, a}); + grammar3.addRule(A, {B, a}); + grammar3.addRule(A, {c}); + grammar3.addRule(B, {c, b}); + grammar3.addRule(B, {c, b, Bprimed}); + grammar3.addRule(Bprimed, {a, b, Bprimed}); + grammar3.addRule(Bprimed, {a, b}); + + CAPTURE ( factory::StringDataFactory::toString( grammar1 ) ); + CAPTURE ( factory::StringDataFactory::toString( grammar2 ) ); + CAPTURE ( factory::StringDataFactory::toString( grammar3 ) ); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::EpsilonFreeCFG < > grammar1(A); + grammar1.setNonterminalAlphabet({A, B, C}); + grammar1.setTerminalAlphabet({a, b}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(A, {a}); + grammar1.addRule(B, {C, A}); + grammar1.addRule(B, {A, b}); + grammar1.addRule(C, {A, B}); + grammar1.addRule(C, {C, C}); + grammar1.addRule(C, {a}); + + DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType Cprimed = common::createUnique(C, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + CAPTURE ( factory::StringDataFactory::toString( grammar1 ) ); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(A); + grammar3.setNonterminalAlphabet({A, B, Bprimed, C, Cprimed}); + grammar3.setTerminalAlphabet({a, b}); + grammar3.addRule(A, {B, C}); + grammar3.addRule(A, {a}); + grammar3.addRule(B, {C, A}); + grammar3.addRule(B, {a, b}); + grammar3.addRule(B, {C, A, Bprimed}); + grammar3.addRule(B, {a, b, Bprimed}); + grammar3.addRule(Bprimed, {C, b, Bprimed}); + grammar3.addRule(Bprimed, {C, b}); + grammar3.addRule(C, {a, b, C, B}); + grammar3.addRule(C, {a, b, Bprimed, C, B}); + grammar3.addRule(C, {a, B}); + grammar3.addRule(C, {a}); + grammar3.addRule(C, {a, b, C, B, Cprimed}); + grammar3.addRule(C, {a, b, Bprimed, C, B, Cprimed}); + grammar3.addRule(C, {a, B, Cprimed}); + grammar3.addRule(C, {a, Cprimed}); + grammar3.addRule(Cprimed, {A, C, B, Cprimed}); + grammar3.addRule(Cprimed, {A, Bprimed, C, B, Cprimed}); + grammar3.addRule(Cprimed, {C, Cprimed}); + grammar3.addRule(Cprimed, {A, C, B}); + grammar3.addRule(Cprimed, {A, Bprimed, C, B}); + grammar3.addRule(Cprimed, {C}); + + CAPTURE ( factory::StringDataFactory::toString( grammar2 ) ); + CAPTURE ( factory::StringDataFactory::toString( grammar3 ) ); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::EpsilonFreeCFG < > grammar1(A); + grammar1.setNonterminalAlphabet({A, B, C}); + grammar1.setTerminalAlphabet({a, b}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(A, {a}); + grammar1.addRule(B, {C, A}); + grammar1.addRule(B, {A, b}); + grammar1.addRule(C, {A, B}); + grammar1.addRule(C, {C, C}); + grammar1.addRule(C, {a}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::LeftRecursionRemover::remove(grammar1); + + CHECK(grammar::generate::GenerateUpToLength::generate(grammar1, 7) == grammar::generate::GenerateUpToLength::generate(grammar2, 7)); + } + } } diff --git a/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.h b/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.h deleted file mode 100644 index 8e22bbbdf6..0000000000 --- a/alib2algo/test-src/grammar/simplify/GrammarLeftRecursionRemoverTest.h +++ /dev/null @@ -1,27 +0,0 @@ -#ifndef GRAMMAR_LEFT_RECURSION_REMOVER_TEST_H_ -#define GRAMMAR_LEFT_RECURSION_REMOVER_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarLeftRecursionRemoverTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarLeftRecursionRemoverTest ); - CPPUNIT_TEST( testRemoveLefRecursion1 ); - CPPUNIT_TEST( testRemoveLefRecursion2 ); - CPPUNIT_TEST( testRemoveLefRecursion3 ); - CPPUNIT_TEST( testRemoveLefRecursion4 ); - CPPUNIT_TEST( testRemoveLefRecursion5 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRemoveLefRecursion1(); - void testRemoveLefRecursion2(); - void testRemoveLefRecursion3(); - void testRemoveLefRecursion4(); - void testRemoveLefRecursion5(); -}; - -#endif /* GRAMMAR_LEFT_RECURSION_REMOVER_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.cpp b/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.cpp index 6ea9683ca4..d68d7e4e16 100644 --- a/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.cpp +++ b/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.cpp @@ -1,130 +1,123 @@ -#include "GrammarSimpleRulesRemoverTest.h" +#include <catch2/catch.hpp> #include "grammar/simplify/SimpleRulesRemover.h" #include "grammar/ContextFree/CFG.h" #include "grammar/ContextFree/EpsilonFreeCFG.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarSimpleRulesRemoverTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarSimpleRulesRemoverTest ); - -void GrammarSimpleRulesRemoverTest::setUp() { -} - -void GrammarSimpleRulesRemoverTest::tearDown() { -} - -void GrammarSimpleRulesRemoverTest::testRemoveSimpleRulesRules1() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - - grammar::CFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - - grammar::CFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); - - grammar::CFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b}); - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarSimpleRulesRemoverTest::testRemoveSimpleRulesRules2() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::CFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {a, A, d, D}); - grammar1.addRule(A, {B}); - grammar1.addRule(B, {b, B, c, C}); - grammar1.addRule(B, {}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {}); - - grammar::CFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); - - grammar::CFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b, c, d}); - grammar3.addRule(S, {a, A, d, D}); - grammar3.addRule(S, {b, B, c, C}); - grammar3.addRule(S, {}); - grammar3.addRule(A, {a, A, d, D}); - grammar3.addRule(A, {b, B, c, C}); - grammar3.addRule(A, {}); - grammar3.addRule(B, {b, B, c, C}); - grammar3.addRule(B, {}); - grammar3.addRule(C, {c, C}); - grammar3.addRule(C, {}); - grammar3.addRule(D, {d, D}); - grammar3.addRule(D, {}); - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarSimpleRulesRemoverTest::testRemoveSimpleRulesRules3() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType('a'); - DefaultSymbolType b = DefaultSymbolType('b'); - DefaultSymbolType c = DefaultSymbolType('c'); - DefaultSymbolType d = DefaultSymbolType('d'); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c, d}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {a, A, d, D}); - grammar1.addRule(A, {B}); - grammar1.addRule(B, {b, B, c, C}); - grammar1.addRule(B, {c}); - grammar1.addRule(C, {c, C}); - grammar1.addRule(C, {b}); - grammar1.addRule(D, {d, D}); - grammar1.addRule(D, {a}); - - grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); - - grammar::EpsilonFreeCFG < > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D}); - grammar3.setTerminalAlphabet({a, b, c, d}); - grammar3.addRule(S, {a, A, d, D}); - grammar3.addRule(S, {b, B, c, C}); - grammar3.addRule(S, {c}); - grammar3.addRule(A, {a, A, d, D}); - grammar3.addRule(A, {b, B, c, C}); - grammar3.addRule(A, {c}); - grammar3.addRule(B, {b, B, c, C}); - grammar3.addRule(B, {c}); - grammar3.addRule(C, {c, C}); - grammar3.addRule(C, {b}); - grammar3.addRule(D, {d, D}); - grammar3.addRule(D, {a}); - - CPPUNIT_ASSERT(grammar2 == grammar3); +TEST_CASE ( "Simple rules remover", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test CFG" ) { + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + + grammar::CFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + + grammar::CFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); + + grammar::CFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b}); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::CFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {a, A, d, D}); + grammar1.addRule(A, {B}); + grammar1.addRule(B, {b, B, c, C}); + grammar1.addRule(B, {}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {}); + + grammar::CFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); + + grammar::CFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b, c, d}); + grammar3.addRule(S, {a, A, d, D}); + grammar3.addRule(S, {b, B, c, C}); + grammar3.addRule(S, {}); + grammar3.addRule(A, {a, A, d, D}); + grammar3.addRule(A, {b, B, c, C}); + grammar3.addRule(A, {}); + grammar3.addRule(B, {b, B, c, C}); + grammar3.addRule(B, {}); + grammar3.addRule(C, {c, C}); + grammar3.addRule(C, {}); + grammar3.addRule(D, {d, D}); + grammar3.addRule(D, {}); + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType('a'); + DefaultSymbolType b = DefaultSymbolType('b'); + DefaultSymbolType c = DefaultSymbolType('c'); + DefaultSymbolType d = DefaultSymbolType('d'); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c, d}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {a, A, d, D}); + grammar1.addRule(A, {B}); + grammar1.addRule(B, {b, B, c, C}); + grammar1.addRule(B, {c}); + grammar1.addRule(C, {c, C}); + grammar1.addRule(C, {b}); + grammar1.addRule(D, {d, D}); + grammar1.addRule(D, {a}); + + grammar::EpsilonFreeCFG < > grammar2 = grammar::simplify::SimpleRulesRemover::remove(grammar1); + + grammar::EpsilonFreeCFG < > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D}); + grammar3.setTerminalAlphabet({a, b, c, d}); + grammar3.addRule(S, {a, A, d, D}); + grammar3.addRule(S, {b, B, c, C}); + grammar3.addRule(S, {c}); + grammar3.addRule(A, {a, A, d, D}); + grammar3.addRule(A, {b, B, c, C}); + grammar3.addRule(A, {c}); + grammar3.addRule(B, {b, B, c, C}); + grammar3.addRule(B, {c}); + grammar3.addRule(C, {c, C}); + grammar3.addRule(C, {b}); + grammar3.addRule(D, {d, D}); + grammar3.addRule(D, {a}); + + CHECK(grammar2 == grammar3); + } + } } diff --git a/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.h b/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.h deleted file mode 100644 index fe17db1714..0000000000 --- a/alib2algo/test-src/grammar/simplify/GrammarSimpleRulesRemoverTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef GRAMMAR_SIMPLE_RULES_REMOVER_TEST_H_ -#define GRAMMAR_SIMPLE_RULES_REMOVER_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarSimpleRulesRemoverTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarSimpleRulesRemoverTest ); - CPPUNIT_TEST( testRemoveSimpleRulesRules1 ); - CPPUNIT_TEST( testRemoveSimpleRulesRules2 ); - CPPUNIT_TEST( testRemoveSimpleRulesRules3 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRemoveSimpleRulesRules1(); - void testRemoveSimpleRulesRules2(); - void testRemoveSimpleRulesRules3(); -}; - -#endif /* GRAMMAR_SIMPLE_RULES_REMOVER_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.cpp b/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.cpp index c66a594015..ad45309c68 100644 --- a/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.cpp +++ b/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.cpp @@ -1,4 +1,4 @@ -#include "GrammarToCNFTest.h" +#include <catch2/catch.hpp> #include "grammar/simplify/ToCNF.h" @@ -9,94 +9,86 @@ #include <grammar/Grammar.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarToCNFTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarToCNFTest ); - -void GrammarToCNFTest::setUp() { -} - -void GrammarToCNFTest::tearDown() { -} - -void GrammarToCNFTest::testToCNFRules1() { - std::string S = "S"; - std::string A = "A"; - std::string B = "B"; - std::string C = "C"; - std::string D = "D"; - - char a = 'a'; - char b = 'b'; - - grammar::CFG < char, std::string > grammar1 ( S ); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - - grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar2 = grammar::simplify::ToCNF::convert ( grammar1 ); - - grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar3 ( ext::vector < ext::variant < char, std::string > > { S } ); - grammar3.setNonterminalAlphabet({{S}, {A}, {B}, {C}, {D}, {a}, {b}}); - grammar3.setTerminalAlphabet({a, b}); - grammar3.addRule ( ext::vector < ext::variant < char, std::string > > { a }, a); - grammar3.addRule ( ext::vector < ext::variant < char, std::string > > { b }, b); - - std::cout << grammar2 << std::endl; - std::cout << grammar3 << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarToCNFTest::testToCNFRules2() { - std::string S = "S"; - std::string X = "X"; - std::string Y = "Y"; - - char a = 'a'; - char b = 'b'; - char c = 'c'; - - grammar::CFG < char, std::string > grammar1 ( S ); - grammar1.setNonterminalAlphabet({S, X, Y}); - grammar1.setTerminalAlphabet({a, b, c}); - grammar1.addRule(S, {a, X, b, X}); - grammar1.addRule(X, {a, Y}); - grammar1.addRule(X, {b, Y}); - grammar1.addRule(X, {}); - grammar1.addRule(Y, {X}); - grammar1.addRule(Y, {c}); - - grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar2 = grammar::simplify::ToCNF::convert(grammar1); - - ext::vector < ext::variant < char, std::string > > Xb { X, b }; - ext::vector < ext::variant < char, std::string > > aX { a, X }; - ext::vector < ext::variant < char, std::string > > bX { b, X }; - - grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar3 ( ext::vector < ext::variant < char, std::string > > { S } ); - grammar3.setNonterminalAlphabet({{S}, {X}, {Y}, {a}, {b}, {c}, {Xb}, {aX}, {bX}}); - grammar3.setTerminalAlphabet({a, b, c}); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { aX }, ext::vector < ext::variant < char, std::string > > { bX } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { bX } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Xb } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { b } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { aX }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { X } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { bX }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { X } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Xb }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { X }, ext::vector < ext::variant < char, std::string > > { b } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Y } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { Y } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, a); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, b); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Y } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { Y } ) ); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, a); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, b); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, c); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { a }, a); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { b }, b); - grammar3.addRule( ext::vector < ext::variant < char, std::string > > { c }, c); - - std::cout << grammar2 << std::endl; - std::cout << grammar3 << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); +TEST_CASE ( "Test to CNF", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test CFG" ) { + { + std::string S = "S"; + std::string A = "A"; + std::string B = "B"; + std::string C = "C"; + std::string D = "D"; + + char a = 'a'; + char b = 'b'; + + grammar::CFG < char, std::string > grammar1 ( S ); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + + grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar2 = grammar::simplify::ToCNF::convert ( grammar1 ); + + grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar3 ( ext::vector < ext::variant < char, std::string > > { S } ); + grammar3.setNonterminalAlphabet({{S}, {A}, {B}, {C}, {D}, {a}, {b}}); + grammar3.setTerminalAlphabet({a, b}); + grammar3.addRule ( ext::vector < ext::variant < char, std::string > > { a }, a); + grammar3.addRule ( ext::vector < ext::variant < char, std::string > > { b }, b); + + CAPTURE ( grammar2, grammar3 ); + + CHECK(grammar2 == grammar3); + } + { + std::string S = "S"; + std::string X = "X"; + std::string Y = "Y"; + + char a = 'a'; + char b = 'b'; + char c = 'c'; + + grammar::CFG < char, std::string > grammar1 ( S ); + grammar1.setNonterminalAlphabet({S, X, Y}); + grammar1.setTerminalAlphabet({a, b, c}); + grammar1.addRule(S, {a, X, b, X}); + grammar1.addRule(X, {a, Y}); + grammar1.addRule(X, {b, Y}); + grammar1.addRule(X, {}); + grammar1.addRule(Y, {X}); + grammar1.addRule(Y, {c}); + + grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar2 = grammar::simplify::ToCNF::convert(grammar1); + + ext::vector < ext::variant < char, std::string > > Xb { X, b }; + ext::vector < ext::variant < char, std::string > > aX { a, X }; + ext::vector < ext::variant < char, std::string > > bX { b, X }; + + grammar::CNF < char, ext::vector < ext::variant < char, std::string > > > grammar3 ( ext::vector < ext::variant < char, std::string > > { S } ); + grammar3.setNonterminalAlphabet({{S}, {X}, {Y}, {a}, {b}, {c}, {Xb}, {aX}, {bX}}); + grammar3.setTerminalAlphabet({a, b, c}); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { aX }, ext::vector < ext::variant < char, std::string > > { bX } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { bX } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Xb } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { S }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { b } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { aX }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { X } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { bX }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { X } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Xb }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { X }, ext::vector < ext::variant < char, std::string > > { b } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Y } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { Y } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, a); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { X }, b); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { a }, ext::vector < ext::variant < char, std::string > > { Y } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, ext::make_pair ( ext::vector < ext::variant < char, std::string > > { b }, ext::vector < ext::variant < char, std::string > > { Y } ) ); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, a); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, b); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { Y }, c); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { a }, a); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { b }, b); + grammar3.addRule( ext::vector < ext::variant < char, std::string > > { c }, c); + + CAPTURE ( grammar2, grammar3 ); + + CHECK(grammar2 == grammar3); + } + } } diff --git a/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.h b/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.h deleted file mode 100644 index 85081c5b4d..0000000000 --- a/alib2algo/test-src/grammar/simplify/GrammarToCNFTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef GRAMMAR_TO_CNF_TEST_H_ -#define GRAMMAR_TO_CNF_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarToCNFTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarToCNFTest ); - CPPUNIT_TEST( testToCNFRules1 ); - CPPUNIT_TEST( testToCNFRules2 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testToCNFRules1(); - void testToCNFRules2(); -}; - -#endif /* GRAMMAR_TO_CNF_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.cpp b/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.cpp index 81174c8231..006e9d7235 100644 --- a/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.cpp +++ b/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.cpp @@ -1,4 +1,4 @@ -#include "GrammarToGNFTest.h" +#include <catch2/catch.hpp> #include "grammar/simplify/ToGNF.h" #include "grammar/generate/GenerateUpToLength.h" @@ -12,165 +12,148 @@ #include "container/string/ObjectsVariant.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( GrammarToGNFTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( GrammarToGNFTest ); - -void GrammarToGNFTest::setUp() { -} - -void GrammarToGNFTest::tearDown() { -} - -void GrammarToGNFTest::testRemoveToGNFRules1() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType("a"); - DefaultSymbolType b = DefaultSymbolType("b"); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b}); - - DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, C, D, aprimed, bprimed}); - grammar3.setTerminalAlphabet({a, b}); - grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - - std::cout << grammar2 << std::endl; - std::cout << grammar3 << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarToGNFTest::testRemoveToGNFRules2() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - DefaultSymbolType D = DefaultSymbolType("D"); - - DefaultSymbolType a = DefaultSymbolType("a"); - DefaultSymbolType b = DefaultSymbolType("b"); - DefaultSymbolType c = DefaultSymbolType("c"); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C, D}); - grammar1.setTerminalAlphabet({a, b, c}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {A, a}); - grammar1.addRule(A, {A, b}); - grammar1.addRule(A, {c}); - - DefaultSymbolType Aprimed = common::createUnique(A, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType cprimed = common::createUnique(c, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - std::cout << grammar1 << std::endl; - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, Aprimed, B, C, D, aprimed, bprimed, cprimed}); - grammar3.setTerminalAlphabet({a, b, c}); - grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); - grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); - grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(Aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); - grammar3.addRule(Aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(Aprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); - grammar3.addRule(Aprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(cprimed, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - - std::cout << grammar2 << std::endl; - std::cout << grammar3 << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarToGNFTest::testRemoveToGNFRules3() { - DefaultSymbolType S = DefaultSymbolType("S"); - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - - DefaultSymbolType a = DefaultSymbolType("a"); - DefaultSymbolType b = DefaultSymbolType("b"); - DefaultSymbolType c = DefaultSymbolType("c"); - - grammar::EpsilonFreeCFG < > grammar1(S); - grammar1.setNonterminalAlphabet({S, A, B, C}); - grammar1.setTerminalAlphabet({a, b, c}); - grammar1.addRule(S, {A}); - grammar1.addRule(A, {B, a}); - grammar1.addRule(B, {A, b}); - grammar1.addRule(A, {c}); - - DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - DefaultSymbolType cprimed = common::createUnique(c, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); - - std::cout << grammar1 << std::endl; - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); - grammar3.setNonterminalAlphabet({S, A, B, Bprimed, C, aprimed, bprimed, cprimed}); - grammar3.setTerminalAlphabet({a, b, c}); - grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed, aprimed})); - grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, aprimed})); - grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, aprimed})); - grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed, aprimed})); - grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(B, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed})); - grammar3.addRule(B, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed})); - grammar3.addRule(Bprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed})); - grammar3.addRule(Bprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed})); - grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - grammar3.addRule(cprimed, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); - - std::cout << grammar2 << std::endl; - std::cout << grammar3 << std::endl; - - CPPUNIT_ASSERT(grammar2 == grammar3); -} - -void GrammarToGNFTest::testRemoveToGNFRules4() { - DefaultSymbolType A = DefaultSymbolType("A"); - DefaultSymbolType B = DefaultSymbolType("B"); - DefaultSymbolType C = DefaultSymbolType("C"); - - DefaultSymbolType a = DefaultSymbolType("a"); - DefaultSymbolType b = DefaultSymbolType("b"); - - grammar::EpsilonFreeCFG < > grammar1(A); - grammar1.setNonterminalAlphabet({A, B, C}); - grammar1.setTerminalAlphabet({a, b}); - grammar1.addRule(A, {B, C}); - grammar1.addRule(A, {a}); - grammar1.addRule(B, {C, A}); - grammar1.addRule(B, {A, b}); - grammar1.addRule(C, {A, B}); - grammar1.addRule(C, {C, C}); - grammar1.addRule(C, {a}); - - grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); - - CPPUNIT_ASSERT(grammar::generate::GenerateUpToLength::generate(grammar1, 7) == grammar::generate::GenerateUpToLength::generate(grammar2, 7)); +TEST_CASE ( "Test to GNF", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test CFG" ) { + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType("a"); + DefaultSymbolType b = DefaultSymbolType("b"); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b}); + + DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, C, D, aprimed, bprimed}); + grammar3.setTerminalAlphabet({a, b}); + grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + + CAPTURE ( grammar2, grammar3 ) ; + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + DefaultSymbolType D = DefaultSymbolType("D"); + + DefaultSymbolType a = DefaultSymbolType("a"); + DefaultSymbolType b = DefaultSymbolType("b"); + DefaultSymbolType c = DefaultSymbolType("c"); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C, D}); + grammar1.setTerminalAlphabet({a, b, c}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {A, a}); + grammar1.addRule(A, {A, b}); + grammar1.addRule(A, {c}); + + DefaultSymbolType Aprimed = common::createUnique(A, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType cprimed = common::createUnique(c, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, Aprimed, B, C, D, aprimed, bprimed, cprimed}); + grammar3.setTerminalAlphabet({a, b, c}); + grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); + grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); + grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(Aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); + grammar3.addRule(Aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(Aprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{Aprimed})); + grammar3.addRule(Aprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(cprimed, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + + CAPTURE ( grammar1, grammar2, grammar3 ) ; + + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType S = DefaultSymbolType("S"); + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + + DefaultSymbolType a = DefaultSymbolType("a"); + DefaultSymbolType b = DefaultSymbolType("b"); + DefaultSymbolType c = DefaultSymbolType("c"); + + grammar::EpsilonFreeCFG < > grammar1(S); + grammar1.setNonterminalAlphabet({S, A, B, C}); + grammar1.setTerminalAlphabet({a, b, c}); + grammar1.addRule(S, {A}); + grammar1.addRule(A, {B, a}); + grammar1.addRule(B, {A, b}); + grammar1.addRule(A, {c}); + + DefaultSymbolType Bprimed = common::createUnique(B, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType aprimed = common::createUnique(a, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType bprimed = common::createUnique(b, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + DefaultSymbolType cprimed = common::createUnique(c, grammar1.getTerminalAlphabet(), grammar1.getNonterminalAlphabet()); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar3(S); + grammar3.setNonterminalAlphabet({S, A, B, Bprimed, C, aprimed, bprimed, cprimed}); + grammar3.setTerminalAlphabet({a, b, c}); + grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed, aprimed})); + grammar3.addRule(S, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, aprimed})); + grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, aprimed})); + grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed, aprimed})); + grammar3.addRule(A, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(B, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed})); + grammar3.addRule(B, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed})); + grammar3.addRule(Bprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed, Bprimed})); + grammar3.addRule(Bprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{bprimed})); + grammar3.addRule(aprimed, ext::make_pair(a, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(bprimed, ext::make_pair(b, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + grammar3.addRule(cprimed, ext::make_pair(c, ext::vector<ext::variant<DefaultSymbolType,DefaultSymbolType>>{})); + + CAPTURE ( grammar1, grammar2, grammar3 ); + CHECK(grammar2 == grammar3); + } + { + DefaultSymbolType A = DefaultSymbolType("A"); + DefaultSymbolType B = DefaultSymbolType("B"); + DefaultSymbolType C = DefaultSymbolType("C"); + + DefaultSymbolType a = DefaultSymbolType("a"); + DefaultSymbolType b = DefaultSymbolType("b"); + + grammar::EpsilonFreeCFG < > grammar1(A); + grammar1.setNonterminalAlphabet({A, B, C}); + grammar1.setTerminalAlphabet({a, b}); + grammar1.addRule(A, {B, C}); + grammar1.addRule(A, {a}); + grammar1.addRule(B, {C, A}); + grammar1.addRule(B, {A, b}); + grammar1.addRule(C, {A, B}); + grammar1.addRule(C, {C, C}); + grammar1.addRule(C, {a}); + + grammar::GNF < DefaultSymbolType, ext::variant < DefaultSymbolType, DefaultSymbolType > > grammar2 = grammar::simplify::ToGNF::convert(grammar1); + + CHECK(grammar::generate::GenerateUpToLength::generate(grammar1, 7) == grammar::generate::GenerateUpToLength::generate(grammar2, 7)); + } + } } diff --git a/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.h b/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.h deleted file mode 100644 index d47c6f6537..0000000000 --- a/alib2algo/test-src/grammar/simplify/GrammarToGNFTest.h +++ /dev/null @@ -1,25 +0,0 @@ -#ifndef GRAMMAR_TO_GNF_TEST_H_ -#define GRAMMAR_TO_GNF_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GrammarToGNFTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( GrammarToGNFTest ); - CPPUNIT_TEST( testRemoveToGNFRules1 ); - CPPUNIT_TEST( testRemoveToGNFRules2 ); - CPPUNIT_TEST( testRemoveToGNFRules3 ); - CPPUNIT_TEST( testRemoveToGNFRules4 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRemoveToGNFRules1(); - void testRemoveToGNFRules2(); - void testRemoveToGNFRules3(); - void testRemoveToGNFRules4(); -}; - -#endif /* GRAMMAR_TO_GNF_TEST_H_ */ diff --git a/alib2algo/test-src/grammar/simplify/TrimTest.cpp b/alib2algo/test-src/grammar/simplify/TrimTest.cpp new file mode 100644 index 0000000000..2113e4e457 --- /dev/null +++ b/alib2algo/test-src/grammar/simplify/TrimTest.cpp @@ -0,0 +1,34 @@ +#include <catch2/catch.hpp> + +#include "grammar/simplify/Trim.h" +#include "grammar/Regular/RightRG.h" + +TEST_CASE ( "Trim Grammar", "[unit][algo][grammar][simplify]" ) { + SECTION ( "Test CFG" ) { + + grammar::RightRG < > rrGrammar(DefaultSymbolType(1)); + + rrGrammar.addNonterminalSymbol(DefaultSymbolType(1)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(4)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(5)); + rrGrammar.addNonterminalSymbol(DefaultSymbolType(6)); + rrGrammar.addTerminalSymbol(DefaultSymbolType("a")); + rrGrammar.addTerminalSymbol(DefaultSymbolType("b")); + + rrGrammar.addRule(DefaultSymbolType(1), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); + rrGrammar.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); + rrGrammar.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); + + rrGrammar.addRule(DefaultSymbolType(4), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(5))); + rrGrammar.addRule(DefaultSymbolType(5), DefaultSymbolType("a")); + rrGrammar.addRule(DefaultSymbolType(5), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(2))); + rrGrammar.addRule(DefaultSymbolType(6), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(6))); + + grammar::RightRG < > trimed = grammar::simplify::Trim::trim(rrGrammar); + + CHECK(trimed.getNonterminalAlphabet().size() == 3); + } +} + diff --git a/alib2algo/test-src/grammar/toGrammar/rg2rgTest.cpp b/alib2algo/test-src/grammar/toGrammar/rg2rgTest.cpp deleted file mode 100644 index bb1dcada1e..0000000000 --- a/alib2algo/test-src/grammar/toGrammar/rg2rgTest.cpp +++ /dev/null @@ -1,78 +0,0 @@ -#include <alib/list> -#include "rg2rgTest.h" - -#include "grammar/convert/ToGrammarLeftRG.h" -#include "grammar/convert/ToGrammarRightRG.h" - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( rg2rgTest, "grammar" ); -CPPUNIT_TEST_SUITE_REGISTRATION( rg2rgTest ); - -void rg2rgTest::setUp() { -} - -void rg2rgTest::tearDown() { -} - -void rg2rgTest::testConversion() { - grammar::RightRG < > rrGrammar(DefaultSymbolType(1)); - - rrGrammar.addNonterminalSymbol(DefaultSymbolType(1)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); - rrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); - rrGrammar.addTerminalSymbol(DefaultSymbolType("a")); - rrGrammar.addTerminalSymbol(DefaultSymbolType("b")); - - rrGrammar.addRule(DefaultSymbolType(1), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); - rrGrammar.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); - rrGrammar.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); - - grammar::LeftRG < > lrGrammar = grammar::convert::ToGrammarLeftRG::convert(rrGrammar); - - DefaultSymbolType four ( object::AnyObject < int > ( 1, 1 ) ); - grammar::LeftRG < > lrGrammarRef ( four ); - - lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(1)); - lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(2)); - lrGrammarRef.addNonterminalSymbol(DefaultSymbolType(3)); - lrGrammarRef.addTerminalSymbol(DefaultSymbolType("a")); - lrGrammarRef.addTerminalSymbol(DefaultSymbolType("b")); - - lrGrammarRef.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType(1), DefaultSymbolType("a"))); - lrGrammarRef.addRule(DefaultSymbolType(2), DefaultSymbolType("a")); - lrGrammarRef.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType(2), DefaultSymbolType("b"))); - lrGrammarRef.addRule(four, ext::make_pair(DefaultSymbolType(3), DefaultSymbolType("a"))); - - CPPUNIT_ASSERT(lrGrammarRef == lrGrammar); -} - -void rg2rgTest::testConversion2() { - grammar::LeftRG < > lrGrammar(DefaultSymbolType(4)); - - lrGrammar.addNonterminalSymbol(DefaultSymbolType(2)); - lrGrammar.addNonterminalSymbol(DefaultSymbolType(3)); - lrGrammar.addNonterminalSymbol(DefaultSymbolType(4)); - lrGrammar.addTerminalSymbol(DefaultSymbolType("a")); - lrGrammar.addTerminalSymbol(DefaultSymbolType("b")); - - lrGrammar.addRule(DefaultSymbolType(2), DefaultSymbolType("a")); - lrGrammar.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType(2), DefaultSymbolType("b"))); - lrGrammar.addRule(DefaultSymbolType(4), ext::make_pair(DefaultSymbolType(3), DefaultSymbolType("a"))); - - grammar::RightRG < > rrGrammar = grammar::convert::ToGrammarRightRG::convert(lrGrammar); - - DefaultSymbolType five ( object::AnyObject < int > ( 4, 1 ) ); - grammar::RightRG < > rrGrammarRef ( five ); - - rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(2)); - rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(3)); - rrGrammarRef.addNonterminalSymbol(DefaultSymbolType(4)); - rrGrammarRef.addTerminalSymbol(DefaultSymbolType("a")); - rrGrammarRef.addTerminalSymbol(DefaultSymbolType("b")); - - rrGrammarRef.addRule(five, ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(2))); - rrGrammarRef.addRule(DefaultSymbolType(2), ext::make_pair(DefaultSymbolType("b"), DefaultSymbolType(3))); - rrGrammarRef.addRule(DefaultSymbolType(3), DefaultSymbolType("a")); - rrGrammarRef.addRule(DefaultSymbolType(3), ext::make_pair(DefaultSymbolType("a"), DefaultSymbolType(4))); - - CPPUNIT_ASSERT(rrGrammarRef == rrGrammar); -} diff --git a/alib2algo/test-src/grammar/toGrammar/rg2rgTest.h b/alib2algo/test-src/grammar/toGrammar/rg2rgTest.h deleted file mode 100644 index 923e4442d3..0000000000 --- a/alib2algo/test-src/grammar/toGrammar/rg2rgTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef RG2RG_TEST_H_ -#define RG2RG_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class rg2rgTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( rg2rgTest ); - CPPUNIT_TEST( testConversion ); - CPPUNIT_TEST( testConversion2 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testConversion(); - void testConversion2(); -}; - -#endif // RG2RG_TEST_H_ diff --git a/alib2algo/test-src/main.cpp b/alib2algo/test-src/main.cpp index adb58324a1..4ed06df1f7 100644 --- a/alib2algo/test-src/main.cpp +++ b/alib2algo/test-src/main.cpp @@ -1,166 +1,2 @@ -#include <version.hpp> - -#include <tclap/CmdLine.h> - -#include <cppunit/CompilerOutputter.h> -#include <cppunit/extensions/TestFactoryRegistry.h> -#include <cppunit/ui/text/TestRunner.h> -#include <cppunit/TestResultCollector.h> -#include <cppunit/TestResult.h> -#include <cppunit/XmlOutputter.h> - -#include <cppunit/Test.h> -#include <cppunit/TestFailure.h> -#include <cppunit/portability/Stream.h> -#include <cppunit/TestListener.h> -#include <cppunit/SourceLine.h> -#include <cppunit/Exception.h> - -#include <exception/CommonException.h> - -CPPUNIT_NS_BEGIN - -class CPPUNIT_API TestProgressListener : public TestListener -{ -public: - TestProgressListener(); - - virtual ~TestProgressListener(); - - void startTest( Test *test ); - - void addFailure( const TestFailure &failure ); - - void endTest( Test *test ); - - int getResult() const; - - void printResults() const; - -private: - TestProgressListener( const TestProgressListener © ); - - void operator =( const TestProgressListener © ); - -private: - int m_Failures; - int m_Tests; - int m_Assertions; - bool m_lastTestFailed; -}; - -TestProgressListener::TestProgressListener() : m_Failures( 0 ), m_Tests(0), m_Assertions(0), m_lastTestFailed( false ) -{ -} - -TestProgressListener::~TestProgressListener() -{ -} - -void TestProgressListener::startTest( Test * test ) -{ - stdCOut() << test->getName() << ":" << "\n"; - stdCOut().flush(); - - m_lastTestFailed = false; - m_Tests++; -} - -void TestProgressListener::addFailure( const TestFailure &failure ) -{ - stdCOut() << (failure.isError() ? "error" : "assertion") << " : " << failure.failedTestName() << " : " << failure.sourceLine().lineNumber() << "\n"; - stdCOut() << "Exception " << failure.thrownException()->message().details(); - - m_lastTestFailed = true; - if(failure.isError()) m_Failures++; else m_Assertions++; -} - -void TestProgressListener::endTest( Test * test) -{ - stdCOut() << "Result (" << test->getName() << ")"; - stdCOut().flush(); - - if ( !m_lastTestFailed ) - stdCOut() << " : OK"; - else - stdCOut() << " : Fail"; - stdCOut() << "\n\n"; -} - -int TestProgressListener::getResult() const { - return m_Failures + m_Assertions; -} - -void TestProgressListener::printResults() const { - stdCOut() << "Overal result: Tests: " << m_Tests << " Assertions: " << m_Assertions << " Failures: " << m_Failures << "\n"; -} - -CPPUNIT_NS_END - -int main(int argc, char* argv[]) { - try { - TCLAP::CmdLine cmd("Main test binary.", ' ', ALIB_VERSION_INFO); - - TCLAP::MultiArg<std::string> testPathSegments("p", "path", "test path", false, "string" ); - cmd.add( testPathSegments ); - - cmd.parse(argc, argv); - - CppUnit::TestResult controller; - - CppUnit::TestResultCollector result; - controller.addListener( &result ); - - CppUnit::TestProgressListener progressListener; - controller.addListener( &progressListener ); - - CppUnit::Test *suite = NULL; - std::string testPath = ""; - if(testPathSegments.getValue().size() == 0) { - // Get the top level suite from the registry - suite = CppUnit::TestFactoryRegistry::getRegistry().makeTest(); - } else if(testPathSegments.getValue().size() == 1) { - suite = CppUnit::TestFactoryRegistry::getRegistry(testPathSegments.getValue()[0]).makeTest(); - } else { - suite = CppUnit::TestFactoryRegistry::getRegistry(testPathSegments.getValue()[0]).makeTest(); - bool first = true; - for(const std::string& path : testPathSegments.getValue()) { - if(first) { - first = false; - continue; - } - testPath += path + "/"; - } - testPath.pop_back(); - } - - // Adds the test to the list of test to run - CppUnit::TextUi::TestRunner runner; - runner.addTest( suite ); - - // Change the default outputter to a compiler error format outputter - runner.setOutputter( new CppUnit::CompilerOutputter( &runner.result(), std::cerr ) ); - // Run the tests. - runner.run( controller, testPath ); - - progressListener.printResults(); - - std::ofstream xmlFileResults("CppUnitTestResults.xml"); - CppUnit::XmlOutputter xmlOut(&result, xmlFileResults); - xmlOut.write(); - - return progressListener.getResult(); - } catch(const exception::CommonException& exception) { - std::cerr << exception.getCause() << std::endl; - return 1; - } catch(const TCLAP::ArgException& exception) { - std::cerr << exception.error() << std::endl; - return 2; - } catch (const std::exception& exception) { - std::cerr << "Exception caught: " << exception.what() << std::endl; - return 3; - } catch(...) { - std::cerr << "Unknown exception caught." << std::endl; - return 127; - } -} +#define CATCH_CONFIG_MAIN +#include <catch2/catch.hpp> diff --git a/alib2algo/test-src/playTest.cpp b/alib2algo/test-src/playTest.cpp deleted file mode 100644 index 9a53f84156..0000000000 --- a/alib2algo/test-src/playTest.cpp +++ /dev/null @@ -1,89 +0,0 @@ -#include "playTest.h" - -#include <alib/iostream> -#include <cstdlib> -#include <ctime> - -#include "automaton/determinize/Determinize.h" -#include "automaton/generate/RandomAutomatonFactory.h" -#include "automaton/simplify/Minimize.h" -#include "automaton/simplify/Normalize.h" -#include "automaton/simplify/Trim.h" -#include "automaton/simplify/EpsilonRemoverIncoming.h" - -#define TEST_ITERATIONS 100 -#define TEST_AUTOMATON_STATES_MAX 18 -#define TEST_AUTOMATON_DENSITY_MAX 2.5 -#define TEST_AUTOMATON_ALPHABET_MAX 4 - -CPPUNIT_TEST_SUITE_REGISTRATION( playTest ); - -void playTest::setUp() -{ - srand(time(NULL)); -} - -void playTest::tearDown(){} - -automaton::NFA < std::string, unsigned > playTest::randomNFA(void) const -{ - return automaton::generate::RandomAutomatonFactory::generateNFA( - rand() % TEST_AUTOMATON_STATES_MAX + 1, - rand() % TEST_AUTOMATON_ALPHABET_MAX + 1, - true, - static_cast<double> (rand()) / (static_cast<double> (RAND_MAX/TEST_AUTOMATON_DENSITY_MAX)) - ); -} - -automaton::DFA < DefaultSymbolType, unsigned > playTest::mDFA(const automaton::NFA < > & automaton) const -{ - automaton::NFA < > nfa = automaton::simplify::EpsilonRemoverIncoming::remove(automaton); - nfa = automaton::simplify::Trim::trim(nfa); - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa = automaton::determinize::Determinize::determinize(nfa); - dfa = automaton::simplify::Trim::trim(dfa); - dfa = automaton::simplify::Minimize::minimize(dfa); - automaton::DFA < DefaultSymbolType, unsigned > dfa2 = automaton::simplify::Normalize::normalize(dfa); - return dfa2; -} - -/** - * Test case 1: - * - covers: FA -> LRG, FA -> RRG, RRG <-> LRG, RRG -> FA, LRG -> FA - * a. FA -> RRG -> LRG -> FA - * b. FA -> LRG -> RRG -> FA - */ -void playTest::testPlay1() -{ - for(int i = 0; i < TEST_ITERATIONS; i++) - this->case1a(); - for(int i = 0; i < TEST_ITERATIONS; i++) - this->case1b(); -} - -void playTest::case1a(void) const -{ - /* - fa2rg::FAtoRRGConverter fa2rrg; - rg2rg::RightToLeftRegularGrammar rrg2lrg; - rg2fa::LRGtoFAConverter lrg2fa; - - automaton::NFA < > a1 = this->randomNFA(); - automaton::NFA < > a2 = lrg2fa.convert(rrg2lrg.convert(fa2rrg.convert(a1))); - - CPPUNIT_ASSERT(this->mDFA(a1) == this->mDFA(a2)); - */ -} - -void playTest::case1b(void) const -{ - /* - fa2rg::FAtoLRGConverter fa2lrg; - rg2rg::LeftToRightRegularGrammar lrg2rrg; - rg2fa::RRGtoFAConverter rrg2fa; - - automaton::NFA < > a1 = this->randomNFA(); - automaton::NFA < > a2 = rrg2fa.convert(lrg2rrg.convert(fa2lrg.convert(a1))); - - CPPUNIT_ASSERT(this->mDFA(a1) == this->mDFA(a2)); - */ -} diff --git a/alib2algo/test-src/playTest.h b/alib2algo/test-src/playTest.h deleted file mode 100644 index d7f12ed7d3..0000000000 --- a/alib2algo/test-src/playTest.h +++ /dev/null @@ -1,30 +0,0 @@ -#ifndef PLAY_TEST_H_ -#define PLAY_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -#include <automaton/FSM/NFA.h> -#include <automaton/FSM/DFA.h> -#include <string> - -class playTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( playTest ); - CPPUNIT_TEST( testPlay1 ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testPlay1(); - -private: - automaton::NFA < std::string, unsigned > randomNFA(void) const; - automaton::DFA < DefaultSymbolType, unsigned > mDFA(const automaton::NFA < > & automaton) const; - - void case1a(void) const; - void case1b(void) const; -}; - -#endif // PLAY_TEST_H_ diff --git a/alib2algo/test-src/regexp/RegExpTest.cpp b/alib2algo/test-src/regexp/RegExpTest.cpp deleted file mode 100644 index 9ccade215d..0000000000 --- a/alib2algo/test-src/regexp/RegExpTest.cpp +++ /dev/null @@ -1,124 +0,0 @@ -#include "RegExpTest.h" -#include <alib/list> -#include <alib/pair> - -#include "sax/SaxComposeInterface.h" -#include "sax/SaxParseInterface.h" - -#include "regexp/unbounded/UnboundedRegExp.h" -#include <regexp/RegExp.h> - -#include "regexp/glushkov/GlushkovFollow.h" -#include "regexp/glushkov/GlushkovIndexate.h" -#include "regexp/glushkov/GlushkovFirst.h" -#include "regexp/glushkov/GlushkovLast.h" - -#include <factory/StringDataFactory.hpp> -#include <regexp/string/UnboundedRegExp.h> - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( RegExpTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( RegExpTest ); - -void RegExpTest::setUp ( ) { -} - -void RegExpTest::tearDown ( ) { -} - -void RegExpTest::testFirst ( ) { - { - std::string input = "#E* #0*"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > first = regexp::GlushkovFirst::first ( indexedRegExp ); - - CPPUNIT_ASSERT ( first.size ( ) == 0 ); - } - { - std::string input = "#E* a"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > first = regexp::GlushkovFirst::first ( indexedRegExp ); - - CPPUNIT_ASSERT ( first.size ( ) == 1 ); - } -} - -void RegExpTest::testLast ( ) { - { - std::string input = "a+a"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > last = regexp::GlushkovLast::last ( indexedRegExp ); - - CPPUNIT_ASSERT ( last.size ( ) == 2 ); - } - { - std::string input = "(a+a)b"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > last = regexp::GlushkovLast::last ( indexedRegExp ); - - std::cout << last << std::endl; - CPPUNIT_ASSERT ( last.size ( ) == 1 ); - } -} - -void RegExpTest::testFollow ( ) { - { - std::string input = "(a+a)b"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - auto symbolsIter = indexedRegExp.getAlphabet ( ).begin ( ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow1 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow1.size ( ) == 1 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow2 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow2.size ( ) == 1 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow3 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow3.size ( ) == 0 ); - } - { - std::string input = "a+a* (b+a)* c"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); - - auto symbolsIter = indexedRegExp.getAlphabet ( ).begin ( ); - - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow1 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow1.size ( ) == 0 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow2 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow2.size ( ) == 4 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow3 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow3.size ( ) == 3 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow4 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow4.size ( ) == 3 ); - - symbolsIter++; - ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow5 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); - - CPPUNIT_ASSERT ( follow5.size ( ) == 0 ); - } -} diff --git a/alib2algo/test-src/regexp/RegExpTest.h b/alib2algo/test-src/regexp/RegExpTest.h deleted file mode 100644 index 05e38f8c20..0000000000 --- a/alib2algo/test-src/regexp/RegExpTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef REG_EXP_TEST_H_ -#define REG_EXP_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpTest ); - CPPUNIT_TEST( testFirst ); - CPPUNIT_TEST( testLast ); - CPPUNIT_TEST( testFollow ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testFirst(); - void testLast(); - void testFollow(); -}; - -#endif // REG_EXP_TEST_H_ diff --git a/alib2algo/test-src/regexp/convert/ToAutomatonTest.cpp b/alib2algo/test-src/regexp/convert/ToAutomatonTest.cpp new file mode 100644 index 0000000000..09021e7f39 --- /dev/null +++ b/alib2algo/test-src/regexp/convert/ToAutomatonTest.cpp @@ -0,0 +1,81 @@ +#include <catch2/catch.hpp> + +#include <alib/list> +#include <alib/pair> + +#include "regexp/convert/ToAutomatonDerivation.h" +#include "regexp/convert/ToAutomatonGlushkov.h" +#include "regexp/convert/ToAutomatonThompson.h" +#include "automaton/convert/ToRegExpAlgebraic.h" +#include "automaton/determinize/Determinize.h" +#include "automaton/simplify/Minimize.h" +#include "automaton/simplify/Normalize.h" +#include "automaton/simplify/EpsilonRemoverOutgoing.h" + +#include "regexp/unbounded/UnboundedRegExp.h" + +#include "automaton/FSM/NFA.h" +#include <factory/StringDataFactory.hpp> +#include <regexp/string/UnboundedRegExp.h> + + +TEST_CASE ( "RegExp to automaton", "[unit][algo][regexp][convert]" ) { + const std::string input = "a+a* b*"; + + SECTION ( "Thompson" ) { + regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString (input); + + automaton::EpsilonNFA < > enfa1 = regexp::convert::ToAutomatonThompson::convert(regexp1); + + regexp::UnboundedRegExp < > regexp2 ( automaton::convert::ToRegExpAlgebraic::convert( enfa1) ); + + automaton::EpsilonNFA < > enfa2 = regexp::convert::ToAutomatonThompson::convert(regexp2); + + automaton::MultiInitialStateNFA < > nfa1 = automaton::simplify::EpsilonRemoverOutgoing::remove(enfa1); + automaton::MultiInitialStateNFA < > nfa2 = automaton::simplify::EpsilonRemoverOutgoing::remove(enfa2); + + automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa1 = automaton::determinize::Determinize::determinize(nfa1); + automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa2 = automaton::determinize::Determinize::determinize(nfa2); + + automaton::DFA< DefaultSymbolType, unsigned > mdfa1 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa1)); + automaton::DFA< DefaultSymbolType, unsigned > mdfa2 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa2)); + + CHECK( mdfa1 == mdfa2); + } + + SECTION ( "Glushkov" ) { + regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString ( input ); + + automaton::NFA < DefaultSymbolType, ext::pair < DefaultSymbolType, unsigned > > nfa1 = regexp::convert::ToAutomatonGlushkov::convert ( regexp1 ); + + regexp::UnboundedRegExp < > regexp2 = automaton::convert::ToRegExpAlgebraic::convert ( nfa1 ); + + automaton::NFA < DefaultSymbolType, ext::pair < DefaultSymbolType, unsigned > > nfa2 = regexp::convert::ToAutomatonGlushkov::convert(regexp2); + + automaton::DFA < DefaultSymbolType, ext::set < ext::pair < DefaultSymbolType, unsigned > > > dfa1 = automaton::determinize::Determinize::determinize(nfa1); + automaton::DFA < DefaultSymbolType, ext::set < ext::pair < DefaultSymbolType, unsigned > > > dfa2 = automaton::determinize::Determinize::determinize(nfa2); + + automaton::DFA< DefaultSymbolType, unsigned > mdfa1 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa1)); + automaton::DFA< DefaultSymbolType, unsigned > mdfa2 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa2)); + + CHECK( mdfa1 == mdfa2); + } + + SECTION ( "Brzozowski" ) { + regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString (input); + + automaton::DFA < DefaultSymbolType, unsigned > dfa1 = regexp::convert::ToAutomatonDerivation::convert(regexp1); + + regexp::UnboundedRegExp < > regexp2( automaton::convert::ToRegExpAlgebraic::convert ( core::normalize < automaton::DFA < DefaultSymbolType, unsigned > >::eval ( automaton::DFA < DefaultSymbolType, unsigned > ( dfa1 ) ) ) ); + + automaton::DFA < DefaultSymbolType, unsigned > dfa2 = regexp::convert::ToAutomatonDerivation::convert(regexp2); + + automaton::DFA < DefaultSymbolType, unsigned > mdfa1_2 = automaton::simplify::Minimize::minimize(dfa1); + automaton::DFA < DefaultSymbolType, unsigned > mdfa1_3 = automaton::simplify::Normalize::normalize(mdfa1_2); + + automaton::DFA < DefaultSymbolType, unsigned > mdfa2_2 = automaton::simplify::Minimize::minimize(dfa2); + automaton::DFA < DefaultSymbolType, unsigned > mdfa2_3 = automaton::simplify::Normalize::normalize(mdfa2_2); + + CHECK( mdfa1_3 == mdfa2_3); + } +} diff --git a/alib2algo/test-src/regexp/glushkov/GlushkovTest.cpp b/alib2algo/test-src/regexp/glushkov/GlushkovTest.cpp new file mode 100644 index 0000000000..d114d59f4c --- /dev/null +++ b/alib2algo/test-src/regexp/glushkov/GlushkovTest.cpp @@ -0,0 +1,117 @@ +#include <catch2/catch.hpp> +#include <alib/list> +#include <alib/pair> + +#include "sax/SaxComposeInterface.h" +#include "sax/SaxParseInterface.h" + +#include "regexp/unbounded/UnboundedRegExp.h" +#include <regexp/RegExp.h> + +#include "regexp/glushkov/GlushkovFollow.h" +#include "regexp/glushkov/GlushkovIndexate.h" +#include "regexp/glushkov/GlushkovFirst.h" +#include "regexp/glushkov/GlushkovLast.h" + +#include <factory/StringDataFactory.hpp> +#include <regexp/string/UnboundedRegExp.h> + +TEST_CASE ( "RegExp glushkov test", "[unit][algo][regexp][glushkov]" ) { + SECTION ( "First" ) { + { + std::string input = "#E* #0*"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > first = regexp::GlushkovFirst::first ( indexedRegExp ); + + CHECK ( first.size ( ) == 0 ); + } + { + std::string input = "#E* a"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > first = regexp::GlushkovFirst::first ( indexedRegExp ); + + CHECK ( first.size ( ) == 1 ); + } + } + + SECTION ( "Last" ) { + + { + std::string input = "a+a"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > last = regexp::GlushkovLast::last ( indexedRegExp ); + + CHECK ( last.size ( ) == 2 ); + } + { + std::string input = "(a+a)b"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > last = regexp::GlushkovLast::last ( indexedRegExp ); + + CHECK ( last.size ( ) == 1 ); + } + } + + SECTION ( "Follow" ) { + { + std::string input = "(a+a)b"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + auto symbolsIter = indexedRegExp.getAlphabet ( ).begin ( ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow1 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow1.size ( ) == 1 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow2 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow2.size ( ) == 1 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow3 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow3.size ( ) == 0 ); + } + { + std::string input = "a+a* (b+a)* c"; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); + regexp::UnboundedRegExp < ext::pair < DefaultSymbolType, unsigned > > indexedRegExp = regexp::GlushkovIndexate::index ( regexp ); + + auto symbolsIter = indexedRegExp.getAlphabet ( ).begin ( ); + + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow1 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow1.size ( ) == 0 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow2 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow2.size ( ) == 4 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow3 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow3.size ( ) == 3 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow4 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow4.size ( ) == 3 ); + + symbolsIter++; + ext::set < regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > > follow5 = regexp::GlushkovFollow::follow ( indexedRegExp, regexp::UnboundedRegExpSymbol < ext::pair < DefaultSymbolType, unsigned > > ( * symbolsIter ) ); + + CHECK ( follow5.size ( ) == 0 ); + } + } +} diff --git a/alib2algo/test-src/regexp/properties/RegExpEmptyTest.cpp b/alib2algo/test-src/regexp/properties/RegExpEmptyTest.cpp deleted file mode 100644 index c741ea4511..0000000000 --- a/alib2algo/test-src/regexp/properties/RegExpEmptyTest.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include "RegExpEmptyTest.h" - -#include "regexp/properties/RegExpEmpty.h" - -#include <regexp/RegExp.h> - -#include <factory/StringDataFactory.hpp> -#include <regexp/string/UnboundedRegExp.h> - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpEmptyTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpEmptyTest ); - -void RegExpEmptyTest::setUp() { -} - -void RegExpEmptyTest::tearDown() { -} - -void RegExpEmptyTest::testRegExpEmpty() { - { - std::string input = "(#E #0 ) + ( #0 a + (b ( #0 (a*) ) ) )"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(regexp::properties::RegExpEmpty::languageIsEmpty(re)); - } - { - std::string input = "(#E + a ) + ( #0 a + (b ( #0 (a*) ) ) )"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(! regexp::properties::RegExpEmpty::languageIsEmpty(re)); - } -} diff --git a/alib2algo/test-src/regexp/properties/RegExpEmptyTest.h b/alib2algo/test-src/regexp/properties/RegExpEmptyTest.h deleted file mode 100644 index 3c651fcaa3..0000000000 --- a/alib2algo/test-src/regexp/properties/RegExpEmptyTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef REGEXPEMPTY_TEST_H_ -#define REGEXPEMPTY_TEST_H_ - -#include <alib/string> - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpEmptyTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpEmptyTest ); - CPPUNIT_TEST( testRegExpEmpty ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRegExpEmpty(); -}; - -#endif /* REGEXPEMPTY_TEST_H_ */ diff --git a/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.cpp b/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.cpp deleted file mode 100644 index 6809422d1a..0000000000 --- a/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include "RegExpEpsilonTest.h" - -#include "regexp/properties/RegExpEpsilon.h" - -#include <factory/StringDataFactory.hpp> -#include <regexp/string/UnboundedRegExp.h> - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpEpsilonTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpEpsilonTest ); - -void RegExpEpsilonTest::setUp() { -} - -void RegExpEpsilonTest::tearDown() { -} - -void RegExpEpsilonTest::testRegExpEpsilon() { - { - std::string input = "#E + ( (a #E) + a*)"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "( a* )( a* )"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "a + #0"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "#E + a #E + a*"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "a* a*"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "a s d #E + #E #0"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } - { - std::string input = "a + #0"; - regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); - - CPPUNIT_ASSERT(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); - } -} diff --git a/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.h b/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.h deleted file mode 100644 index 3d7c5ff416..0000000000 --- a/alib2algo/test-src/regexp/properties/RegExpEpsilonTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef REGEXPEPSILON_TEST_H_ -#define REGEXPEPSILON_TEST_H_ - -#include <alib/string> - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpEpsilonTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpEpsilonTest ); - CPPUNIT_TEST( testRegExpEpsilon ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRegExpEpsilon(); -}; - -#endif /* REGEXPEPSILON_TEST_H_ */ diff --git a/alib2algo/test-src/regexp/properties/RegExpPropertiesTest.cpp b/alib2algo/test-src/regexp/properties/RegExpPropertiesTest.cpp new file mode 100644 index 0000000000..eb5507828e --- /dev/null +++ b/alib2algo/test-src/regexp/properties/RegExpPropertiesTest.cpp @@ -0,0 +1,69 @@ +#include <catch2/catch.hpp> + +#include "regexp/properties/RegExpEpsilon.h" +#include "regexp/properties/RegExpEmpty.h" + +#include <factory/StringDataFactory.hpp> +#include <regexp/string/UnboundedRegExp.h> + +TEST_CASE ( "RegExp properties", "[unit][algo][regexp][properties]" ) { + SECTION ( "Describes epsilon" ) { + { + std::string input = "#E + ( (a #E) + a*)"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "( a* )( a* )"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "a + #0"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "#E + a #E + a*"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "a* a*"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "a s d #E + #E #0"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + { + std::string input = "a + #0"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(! regexp::properties::RegExpEpsilon::languageContainsEpsilon(re)); + } + } + + SECTION ( "Describes empty language" ) { + { + std::string input = "(#E #0 ) + ( #0 a + (b ( #0 (a*) ) ) )"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(regexp::properties::RegExpEmpty::languageIsEmpty(re)); + } + { + std::string input = "(#E + a ) + ( #0 a + (b ( #0 (a*) ) ) )"; + regexp::UnboundedRegExp < > re = factory::StringDataFactory::fromString (input); + + CHECK(! regexp::properties::RegExpEmpty::languageIsEmpty(re)); + } + } +} diff --git a/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.cpp b/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.cpp index e0c012b417..133b4bd059 100644 --- a/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.cpp +++ b/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.cpp @@ -1,5 +1,6 @@ -#include <alib/list> -#include "RegExpOptimizeTest.h" +#include <catch2/catch.hpp> + +#include <alib/map> #include "regexp/unbounded/UnboundedRegExp.h" @@ -8,281 +9,125 @@ #include <factory/StringDataFactory.hpp> #include <regexp/string/UnboundedRegExp.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpOptimizeTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpOptimizeTest ); - -void RegExpOptimizeTest::setUp() { -} - -void RegExpOptimizeTest::tearDown() { -} - -void RegExpOptimizeTest::testOptimize() { - { - std::string input = "a+a"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); +TEST_CASE ( "RegExp Optimize", "[unit][algo][regexp][simplify]" ) { + SECTION ( "Test simple axioms" ) { + auto testcase = GENERATE ( + std::make_pair ("a+a", "a" ), + std::make_pair ( "(a+a)b + (#0 b + (#0 a + (#0 b + a)))", "a + a b" ), + //std::make_pair ( "a z + a b* b z", "a b* z" ), + std::make_pair ( "a***", "a*" ), + std::make_pair ( "(a*+b*)*", "(a+b)*" ), + std::make_pair ( "(a*b*)*", "(a+b)*" ), + std::make_pair ( "#0*+a*", "a*" ), + std::make_pair ( "a+(a+a)", "a" ) + // std::make_pair ( "(a+b*)(a+b*)*", "(a+b*)*" ), implemented but skipped because ( a + b* )* gets simplified to ( a + b )* FIXME + // std::make_pair ( "(x y)*x", "x(y x)*" ), + ); + + regexp::UnboundedRegExp < > orig = factory::StringDataFactory::fromString ( testcase.first ); + regexp::UnboundedRegExp < > origOpt = regexp::simplify::RegExpOptimize::optimize ( orig ); + regexp::UnboundedRegExp < > expected = factory::StringDataFactory::fromString ( testcase.second ); + + CAPTURE ( testcase.first, testcase.second ); + CAPTURE ( orig, origOpt, expected ); + CHECK ( origOpt == expected ); } - { - std::string input = "(a+a)b + (#0 b + (#0 a + (#0 b + a)))"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a + a b"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); + SECTION ( "Test optimize templated" ) { + regexp::UnboundedRegExpSymbol < char > a ( 'a' ); + regexp::UnboundedRegExpSymbol < char > b ( 'b' ); + regexp::UnboundedRegExpSymbol < char > z ( 'z' ); + + { + regexp::UnboundedRegExpAlternation < char > alt; + alt.appendElement ( a ); + alt.appendElement ( a ); + + regexp::UnboundedRegExp < char > regexp ( regexp::UnboundedRegExpStructure < char > { alt } ); + regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize(regexp); + regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { a } ); + + CAPTURE ( res, regexpRes ); + CHECK ( regexpRes == res ); + } + { + regexp::UnboundedRegExpAlternation < char > alt1; + alt1.appendElement ( a ); + alt1.appendElement ( a ); + regexp::UnboundedRegExpConcatenation < char > con1; + con1.appendElement ( alt1 ); + con1.appendElement ( b ); + + regexp::UnboundedRegExpConcatenation < char > con2; + con2.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); + con2.appendElement ( b ); + regexp::UnboundedRegExpAlternation < char > alt2; + alt2.appendElement ( con2 ); + alt2.appendElement ( a ); + + regexp::UnboundedRegExpConcatenation < char > con3; + con3.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); + con3.appendElement ( a ); + regexp::UnboundedRegExpAlternation < char > alt3; + alt3.appendElement ( con3 ); + alt3.appendElement ( alt2 ); + + regexp::UnboundedRegExpConcatenation < char > con4; + con4.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); + con4.appendElement ( b ); + regexp::UnboundedRegExpAlternation < char > alt4; + alt4.appendElement ( con4 ); + alt4.appendElement ( alt3 ); + + regexp::UnboundedRegExpAlternation < char > alt5; + alt5.appendElement ( con1 ); + alt5.appendElement ( alt4 ); + + regexp::UnboundedRegExp < char > regexp ( regexp::UnboundedRegExpStructure < char > { alt5 } ); + + regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); + + regexp::UnboundedRegExpConcatenation < char > con6; + con6.appendElement ( a ); + con6.appendElement ( b ); + regexp::UnboundedRegExpAlternation < char > alt6; + alt6.appendElement ( a ); + alt6.appendElement ( con6 ); + + regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { alt6 } ); + + CAPTURE ( regexp, res, regexpRes ); + CHECK ( regexpRes == res ); + } + { + regexp::UnboundedRegExpSymbol < char > symb { 'b' }; + regexp::UnboundedRegExpIteration < char > iter { symb }; + + regexp::UnboundedRegExpConcatenation < char > con1; + con1.appendElement ( symb ); + con1.appendElement ( iter ); + + regexp::UnboundedRegExpAlternation < char > alt1; + alt1.appendElement ( con1 ); + + regexp::UnboundedRegExpAlternation < char > alt2; + + regexp::UnboundedRegExpConcatenation < char > con2; + con2.appendElement ( alt1 ); + con2.appendElement ( alt2 ); + + regexp::UnboundedRegExpAlternation < char > alt3; + + regexp::UnboundedRegExpAlternation < char > alt4; + alt4.appendElement ( alt3 ); + alt4.appendElement ( con2 ); + + regexp::UnboundedRegExp < char > regexp( regexp::UnboundedRegExpStructure < char > { alt4 } ); + regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize(regexp); + regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { } ); + + CAPTURE ( regexp, res, regexpRes ); + CHECK ( regexpRes == res ); + } } - /*{ - std::string input = "a z + a b* b z"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a b* z"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - }*/ - { - std::string input = "a***"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - std::string input = "a***"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - std::string input = "(a*+b*)*"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "(a+b)*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - std::string input = "(a*b*)*"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "(a+b)*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - std::string input = "#0*+a*"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - std::string input = "a+(a+a)"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "a"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } -/* { // implemented but skipped because ( a + b* )* gets simplified to ( a + b )* //FIXME - std::string input = "(a+b*)(a+b*)*"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "(a+b*)*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - }*/ - /*{ - std::string input = "(x y)*x"; - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( input ); - - regexp::UnboundedRegExp < > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - std::string inputRes = "x(y x)*"; - regexp::UnboundedRegExp < > regexpRes = factory::StringDataFactory::fromString ( inputRes ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - }*/ - -} - -void RegExpOptimizeTest::testOptimizeTemplated() { - regexp::UnboundedRegExpSymbol < char > a ( 'a' ); - regexp::UnboundedRegExpSymbol < char > b ( 'b' ); - regexp::UnboundedRegExpSymbol < char > z ( 'z' ); - - { - regexp::UnboundedRegExpAlternation < char > alt; - alt.appendElement ( a ); - alt.appendElement ( a ); - - regexp::UnboundedRegExp < char > regexp ( regexp::UnboundedRegExpStructure < char > { alt } ); - - regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize(regexp); - - regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { a } ); - - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - { - regexp::UnboundedRegExpAlternation < char > alt1; - alt1.appendElement ( a ); - alt1.appendElement ( a ); - regexp::UnboundedRegExpConcatenation < char > con1; - con1.appendElement ( alt1 ); - con1.appendElement ( b ); - - regexp::UnboundedRegExpConcatenation < char > con2; - con2.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); - con2.appendElement ( b ); - regexp::UnboundedRegExpAlternation < char > alt2; - alt2.appendElement ( con2 ); - alt2.appendElement ( a ); - - regexp::UnboundedRegExpConcatenation < char > con3; - con3.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); - con3.appendElement ( a ); - regexp::UnboundedRegExpAlternation < char > alt3; - alt3.appendElement ( con3 ); - alt3.appendElement ( alt2 ); - - regexp::UnboundedRegExpConcatenation < char > con4; - con4.appendElement ( regexp::UnboundedRegExpEmpty < char > { } ); - con4.appendElement ( b ); - regexp::UnboundedRegExpAlternation < char > alt4; - alt4.appendElement ( con4 ); - alt4.appendElement ( alt3 ); - - regexp::UnboundedRegExpAlternation < char > alt5; - alt5.appendElement ( con1 ); - alt5.appendElement ( alt4 ); - - regexp::UnboundedRegExp < char > regexp ( regexp::UnboundedRegExpStructure < char > { alt5 } ); - - regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize ( regexp ); - - regexp::UnboundedRegExpConcatenation < char > con6; - con6.appendElement ( a ); - con6.appendElement ( b ); - regexp::UnboundedRegExpAlternation < char > alt6; - alt6.appendElement ( a ); - alt6.appendElement ( con6 ); - - regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { alt6 } ); - - std::cout << regexp << std::endl; - std::cout << res << std::endl; - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - std::cout << std::endl; - { - regexp::UnboundedRegExpSymbol < char > symb { 'b' }; - regexp::UnboundedRegExpIteration < char > iter { symb }; - - regexp::UnboundedRegExpConcatenation < char > con1; - con1.appendElement ( symb ); - con1.appendElement ( iter ); - - regexp::UnboundedRegExpAlternation < char > alt1; - alt1.appendElement ( con1 ); - - regexp::UnboundedRegExpAlternation < char > alt2; - - regexp::UnboundedRegExpConcatenation < char > con2; - con2.appendElement ( alt1 ); - con2.appendElement ( alt2 ); - - regexp::UnboundedRegExpAlternation < char > alt3; - - regexp::UnboundedRegExpAlternation < char > alt4; - alt4.appendElement ( alt3 ); - alt4.appendElement ( con2 ); - - regexp::UnboundedRegExp < char > regexp( regexp::UnboundedRegExpStructure < char > { alt4 } ); - std::cout << regexp << std::endl; - - regexp::UnboundedRegExp < char > res = regexp::simplify::RegExpOptimize::optimize(regexp); - std::cout << res << std::endl; - - regexp::UnboundedRegExp < char > regexpRes( regexp::UnboundedRegExpStructure < char > { } ); - std::cout << regexpRes << std::endl; - - CPPUNIT_ASSERT ( regexpRes == res ); - } - } - diff --git a/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.h b/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.h deleted file mode 100644 index 64241080e0..0000000000 --- a/alib2algo/test-src/regexp/simplify/RegExpOptimizeTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef REG_EXP_OPTIMIZE_TEST_H_ -#define REG_EXP_OPTIMIZE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpOptimizeTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpOptimizeTest ); - CPPUNIT_TEST( testOptimize ); - CPPUNIT_TEST( testOptimizeTemplated ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testOptimize(); - void testOptimizeTemplated(); -}; - -#endif // REG_EXP_OPTIMIZE_TEST_H_ diff --git a/alib2algo/test-src/regexp/toAutomaton/re2faTest.cpp b/alib2algo/test-src/regexp/toAutomaton/re2faTest.cpp deleted file mode 100644 index 203de42432..0000000000 --- a/alib2algo/test-src/regexp/toAutomaton/re2faTest.cpp +++ /dev/null @@ -1,93 +0,0 @@ -#include <alib/list> -#include <alib/pair> -#include "re2faTest.h" - -#include "regexp/convert/ToAutomatonDerivation.h" -#include "regexp/convert/ToAutomatonGlushkov.h" -#include "regexp/convert/ToAutomatonThompson.h" -#include "automaton/convert/ToRegExpAlgebraic.h" -#include "automaton/determinize/Determinize.h" -#include "automaton/simplify/Minimize.h" -#include "automaton/simplify/Normalize.h" -#include "automaton/simplify/EpsilonRemoverOutgoing.h" - -#include "regexp/unbounded/UnboundedRegExp.h" - -#include "automaton/FSM/NFA.h" -#include <factory/StringDataFactory.hpp> -#include <regexp/string/UnboundedRegExp.h> - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( re2faTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( re2faTest ); - -void re2faTest::setUp() { -} - -void re2faTest::tearDown() { -} - -void re2faTest::testThompson() { - std::string input = "a+a* b*"; - regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString (input); - - automaton::EpsilonNFA < > enfa1 = regexp::convert::ToAutomatonThompson::convert(regexp1); - - regexp::UnboundedRegExp < > regexp2 ( automaton::convert::ToRegExpAlgebraic::convert( enfa1) ); - - automaton::EpsilonNFA < > enfa2 = regexp::convert::ToAutomatonThompson::convert(regexp2); - - automaton::MultiInitialStateNFA < > nfa1 = automaton::simplify::EpsilonRemoverOutgoing::remove(enfa1); - automaton::MultiInitialStateNFA < > nfa2 = automaton::simplify::EpsilonRemoverOutgoing::remove(enfa2); - - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa1 = automaton::determinize::Determinize::determinize(nfa1); - automaton::DFA < DefaultSymbolType, ext::set < DefaultStateType > > dfa2 = automaton::determinize::Determinize::determinize(nfa2); - - automaton::DFA< DefaultSymbolType, unsigned > mdfa1 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa1)); - automaton::DFA< DefaultSymbolType, unsigned > mdfa2 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa2)); - - CPPUNIT_ASSERT( mdfa1 == mdfa2); -} - -void re2faTest::testGlushkov() { - std::string input = "a+a*b*"; - regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString ( input ); - - automaton::NFA < DefaultSymbolType, ext::pair < DefaultSymbolType, unsigned > > nfa1 = regexp::convert::ToAutomatonGlushkov::convert ( regexp1 ); - - regexp::UnboundedRegExp < > regexp2 = automaton::convert::ToRegExpAlgebraic::convert ( nfa1 ); - - std::cout << regexp1 << std::endl; - std::cout << regexp2 << std::endl; - - automaton::NFA < DefaultSymbolType, ext::pair < DefaultSymbolType, unsigned > > nfa2 = regexp::convert::ToAutomatonGlushkov::convert(regexp2); - - automaton::DFA < DefaultSymbolType, ext::set < ext::pair < DefaultSymbolType, unsigned > > > dfa1 = automaton::determinize::Determinize::determinize(nfa1); - automaton::DFA < DefaultSymbolType, ext::set < ext::pair < DefaultSymbolType, unsigned > > > dfa2 = automaton::determinize::Determinize::determinize(nfa2); - - automaton::DFA< DefaultSymbolType, unsigned > mdfa1 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa1)); - automaton::DFA< DefaultSymbolType, unsigned > mdfa2 = automaton::simplify::Normalize::normalize(automaton::simplify::Minimize::minimize(dfa2)); - - std::cout << mdfa1 << std::endl; - std::cout << mdfa2 << std::endl; - - CPPUNIT_ASSERT( mdfa1 == mdfa2); -} - -void re2faTest::testBrzozowski() { - std::string input = "a+a* b*"; - regexp::UnboundedRegExp < > regexp1 = factory::StringDataFactory::fromString (input); - - automaton::DFA < DefaultSymbolType, unsigned > dfa1 = regexp::convert::ToAutomatonDerivation::convert(regexp1); - - regexp::UnboundedRegExp < > regexp2( automaton::convert::ToRegExpAlgebraic::convert ( core::normalize < automaton::DFA < DefaultSymbolType, unsigned > >::eval ( automaton::DFA < DefaultSymbolType, unsigned > ( dfa1 ) ) ) ); - - automaton::DFA < DefaultSymbolType, unsigned > dfa2 = regexp::convert::ToAutomatonDerivation::convert(regexp2); - - automaton::DFA < DefaultSymbolType, unsigned > mdfa1_2 = automaton::simplify::Minimize::minimize(dfa1); - automaton::DFA < DefaultSymbolType, unsigned > mdfa1_3 = automaton::simplify::Normalize::normalize(mdfa1_2); - - automaton::DFA < DefaultSymbolType, unsigned > mdfa2_2 = automaton::simplify::Minimize::minimize(dfa2); - automaton::DFA < DefaultSymbolType, unsigned > mdfa2_3 = automaton::simplify::Normalize::normalize(mdfa2_2); - - CPPUNIT_ASSERT( mdfa1_3 == mdfa2_3); -} diff --git a/alib2algo/test-src/regexp/toAutomaton/re2faTest.h b/alib2algo/test-src/regexp/toAutomaton/re2faTest.h deleted file mode 100644 index 0f5454813d..0000000000 --- a/alib2algo/test-src/regexp/toAutomaton/re2faTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef RG2RG_TEST_H_ -#define RG2RG_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class re2faTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( re2faTest ); - CPPUNIT_TEST( testThompson ); - CPPUNIT_TEST( testGlushkov ); - CPPUNIT_TEST( testBrzozowski ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testThompson(); - void testGlushkov(); - void testBrzozowski(); -}; - -#endif // RG2RG_TEST_H_ diff --git a/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.cpp b/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.cpp index 7c1e0d6491..e42273a08f 100644 --- a/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.cpp +++ b/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.cpp @@ -1,4 +1,4 @@ -#include "RegExpConcatenateTest.h" +#include <catch2/catch.hpp> #include "regexp/transform/RegExpConcatenate.h" @@ -8,60 +8,18 @@ #include <factory/StringDataFactory.hpp> #include <regexp/string/UnboundedRegExp.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpConcatenateTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpConcatenateTest ); +TEST_CASE ( "RegExp Concatenate", "[unit][algo][regexp][transform]" ) { + SECTION ( "Test Concat" ) { + auto testcase = GENERATE ( + std::make_tuple ( "(#E a b)", "(#E a c)", "(#E a b)(#E a c)" ), + std::make_tuple ( "(#E a b)", "(#0 #E )", "(#E a b)(#0 #E )" ), + std::make_tuple ( "(#0 #E )", "(#E a b)", "(#0 #E )(#E a b)" ) ); -void RegExpConcatenateTest::setUp() { -} - -void RegExpConcatenateTest::tearDown() { -} - -void RegExpConcatenateTest::testRegExpConcatenate() { - { - std::string input1 = "(#E a b)"; - regexp::UnboundedRegExp < > re1 = factory::StringDataFactory::fromString (input1); - - std::string input2 = "(#E a c)"; - regexp::UnboundedRegExp < > re2 = factory::StringDataFactory::fromString (input2); - - regexp::UnboundedRegExp < > re = regexp::RegExpConcatenate::concatenate(re1, re2); - - std::string inputr = "(#E a b)(#E a c)"; - regexp::UnboundedRegExp < > rer = factory::StringDataFactory::fromString (inputr); - - CPPUNIT_ASSERT(re == rer); - } - { - std::string input1 = "(#E a b)"; - regexp::UnboundedRegExp < > re1 = factory::StringDataFactory::fromString (input1); - - regexp::UnboundedRegExp < > re2(regexp::FormalRegExp < > (regexp::FormalRegExpStructure < DefaultSymbolType > (regexp::FormalRegExpConcatenation < DefaultSymbolType > (regexp::FormalRegExpEmpty < DefaultSymbolType > {}, regexp::FormalRegExpEpsilon < DefaultSymbolType > {})))); - - regexp::UnboundedRegExp < > re = regexp::RegExpConcatenate::concatenate(re1, re2); - - std::string inputr = "(#E a b)(#0 #E )"; - regexp::UnboundedRegExp < > rer = factory::StringDataFactory::fromString (inputr); - - CPPUNIT_ASSERT(re == rer); - } - { - regexp::FormalRegExp < > re1 (regexp::FormalRegExpStructure < DefaultSymbolType > (regexp::FormalRegExpConcatenation < DefaultSymbolType > (regexp::FormalRegExpEmpty < DefaultSymbolType > {}, regexp::FormalRegExpEpsilon < DefaultSymbolType > {}))); - - std::string input2 = "(#E a b)"; - regexp::UnboundedRegExp < > re2 = factory::StringDataFactory::fromString (input2); - - regexp::FormalRegExp < > re = regexp::RegExpConcatenate::concatenate(re1, regexp::FormalRegExp < > ( re2 ) ); - - std::string inputr = "(#0 #E )(#E a b)"; - regexp::UnboundedRegExp < > tmp = factory::StringDataFactory::fromString (inputr); - regexp::FormalRegExp < > rer = regexp::FormalRegExp < > ( tmp ); - - std::cout << tmp.getAlphabet() << std::endl; - std::cout << rer.getAlphabet() << std::endl; + regexp::UnboundedRegExp < > re1 = factory::StringDataFactory::fromString ( std::get < 0 > ( testcase ) ); + regexp::UnboundedRegExp < > re2 = factory::StringDataFactory::fromString ( std::get < 1 > ( testcase ) ); + regexp::UnboundedRegExp < > exp = factory::StringDataFactory::fromString ( std::get < 2 > ( testcase ) ); + regexp::FormalRegExp < > re = regexp::RegExpConcatenate::concatenate( regexp::FormalRegExp < > ( re1 ), regexp::FormalRegExp < > ( re2 ) ); - std::cout << re << std::endl; - std::cout << rer << std::endl; - CPPUNIT_ASSERT(re == rer); + CHECK(re == regexp::FormalRegExp < > ( exp ) ); } } diff --git a/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.h b/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.h deleted file mode 100644 index a48a88b911..0000000000 --- a/alib2algo/test-src/regexp/transform/RegExpConcatenateTest.h +++ /dev/null @@ -1,21 +0,0 @@ -#ifndef REGEXP_CONCATENATE_TEST_H_ -#define REGEXP_CONCATENATE_TEST_H_ - -#include <alib/string> - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpConcatenateTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpConcatenateTest ); - CPPUNIT_TEST( testRegExpConcatenate ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRegExpConcatenate(); -}; - -#endif /* REGEXP_CONCATENATE_TEST_H_ */ diff --git a/alib2algo/test-src/regexp/transform/RegExpDerivationTest.cpp b/alib2algo/test-src/regexp/transform/RegExpDerivationTest.cpp index 44fe7fbca1..c16539c366 100644 --- a/alib2algo/test-src/regexp/transform/RegExpDerivationTest.cpp +++ b/alib2algo/test-src/regexp/transform/RegExpDerivationTest.cpp @@ -1,4 +1,4 @@ -#include "RegExpDerivationTest.h" +#include <catch2/catch.hpp> #include "regexp/transform/RegExpDerivation.h" @@ -11,40 +11,34 @@ #include <string/string/LinearString.h> #include <string/xml/LinearString.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpDerivationTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpDerivationTest ); +TEST_CASE ( "Regexp Derivation", "[unit][algo][grammar][transform]" ) { + SECTION ( "Derivation" ) { + // https://edux.fit.cvut.cz/oppa/BI-AAG/cviceni/aag-cv04.pdf + auto testcase = GENERATE ( + // Exc. 13 + std::make_tuple ( "0 1 0 + 1 0 1 + 0*1 + 1*0", "0", "#E 1 0+#0 0 1+#E 0* 1+#0+#0 1* 0+#E"), + std::make_tuple ( "0 1 0 + 1 0 1 + 0*1 + 1*0", "0 0", "#0 1 0+#0 0+#0 0 1+(#0 0*+#E 0*) 1+#0+#0+#0 1* 0+#0"), -void RegExpDerivationTest::setUp() { -} - -void RegExpDerivationTest::tearDown() { -} - -void RegExpDerivationTest::testRegExpDerivation() { - // https://edux.fit.cvut.cz/oppa/BI-AAG/cviceni/aag-cv04.pdf + // Exc. 14 + std::make_tuple ( "(0 1*0 + 1 0*)*", "1", "(#0 1* 0+#E 0*) (0 1* 0+1 0*)*"), + std::make_tuple ( "(0 1*0 + 1 0*)*", "1 0", "(#0 1* 0+#0 0*+#E 0*) (0 1* 0+1 0*)*+(#E 1* 0+#0 0*) (0 1* 0+1 0*)*"), - // Exc. 13 - this->ExecSingleTest("0 1 0 + 1 0 1 + 0*1 + 1*0", "0", "#E 1 0+#0 0 1+#E 0* 1+#0+#0 1* 0+#E"); - this->ExecSingleTest("0 1 0 + 1 0 1 + 0*1 + 1*0", "0 0", "#0 1 0+#0 0+#0 0 1+(#0 0*+#E 0*) 1+#0+#0+#0 1* 0+#0"); - - // Exc. 14 - this->ExecSingleTest("(0 1*0 + 1 0*)*", "1", "(#0 1* 0+#E 0*) (0 1* 0+1 0*)*"); - this->ExecSingleTest("(0 1*0 + 1 0*)*", "1 0", "(#0 1* 0+#0 0*+#E 0*) (0 1* 0+1 0*)*+(#E 1* 0+#0 0*) (0 1* 0+1 0*)*"); - - // Exc. 15 - this->ExecSingleTest("1 0*1*0", "1 0 0", "#0 0* 1* 0+(#0 0*+#E 0*) 1* 0+#0 1* 0+#E+#0 1* 0+#0"); -} + // Exc. 15 + std::make_tuple ( "1 0*1*0", "1 0 0", "#0 0* 1* 0+(#0 0*+#E 0*) 1* 0+#0 1* 0+#E+#0 1* 0+#0") + ); -void RegExpDerivationTest::ExecSingleTest(std::string regexp_str, std::string string_str, std::string result) { - regexp::UnboundedRegExp < > regexp0 = factory::StringDataFactory::fromString (regexp_str); - ext::deque<sax::Token> tokens = factory::XmlDataFactory::toTokens(regexp0); - regexp::UnboundedRegExp < > regexp = factory::XmlDataFactory::fromTokens (std::move(tokens)); + const std::string & regexp_str = std::get < 0 > ( testcase ); + const std::string & string_str = std::get < 1 > ( testcase ); + const std::string & result = std::get < 2 > ( testcase ); - string::LinearString < > string0 = factory::StringDataFactory::fromString ("\"" + string_str + "\""); - ext::deque<sax::Token> tokens2 = factory::XmlDataFactory::toTokens(string0); - string::LinearString < > string1 = factory::XmlDataFactory::fromTokens (std::move(tokens2)); + regexp::UnboundedRegExp < > regexp0 = factory::StringDataFactory::fromString (regexp_str); + ext::deque<sax::Token> tokens = factory::XmlDataFactory::toTokens(regexp0); + regexp::UnboundedRegExp < > regexp = factory::XmlDataFactory::fromTokens (std::move(tokens)); - std::cout << factory::StringDataFactory::toString(regexp::RegExpDerivation::derivation(regexp, string1)) << " == " << std::endl << result << std::endl << std::endl; + string::LinearString < > string0 = factory::StringDataFactory::fromString ("\"" + string_str + "\""); + ext::deque<sax::Token> tokens2 = factory::XmlDataFactory::toTokens(string0); + string::LinearString < > string1 = factory::XmlDataFactory::fromTokens (std::move(tokens2)); - CPPUNIT_ASSERT(factory::StringDataFactory::toString(regexp::RegExpDerivation::derivation(regexp, string1)) == result); + CHECK(factory::StringDataFactory::toString(regexp::RegExpDerivation::derivation(regexp, string1)) == result); + } } diff --git a/alib2algo/test-src/regexp/transform/RegExpDerivationTest.h b/alib2algo/test-src/regexp/transform/RegExpDerivationTest.h deleted file mode 100644 index 79d4c9bcdf..0000000000 --- a/alib2algo/test-src/regexp/transform/RegExpDerivationTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef REGEXPDERIVATION_TEST_H_ -#define REGEXPDERIVATION_TEST_H_ - -#include <alib/string> - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpDerivationTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpDerivationTest ); - CPPUNIT_TEST( testRegExpDerivation ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRegExpDerivation(); - - void ExecSingleTest(std::string, std::string, std::string); -}; - -#endif /* REGEXPDERIVATION_TEST_H_ */ diff --git a/alib2algo/test-src/regexp/transform/RegExpIntegralTest.cpp b/alib2algo/test-src/regexp/transform/RegExpIntegralTest.cpp index 54c28f62f0..65e2a87dc7 100644 --- a/alib2algo/test-src/regexp/transform/RegExpIntegralTest.cpp +++ b/alib2algo/test-src/regexp/transform/RegExpIntegralTest.cpp @@ -1,4 +1,4 @@ -#include "RegExpIntegralTest.h" +#include <catch2/catch.hpp> #include "regexp/transform/RegExpIntegral.h" @@ -7,27 +7,19 @@ #include <factory/StringDataFactory.hpp> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( RegExpIntegralTest, "regexp" ); -CPPUNIT_TEST_SUITE_REGISTRATION( RegExpIntegralTest ); +TEST_CASE ( "Regexp Integral", "[unit][algo][grammar][transform]" ) { + SECTION ( "Integrals" ) { + // https://edux.fit.cvut.cz/oppa/BI-AAG/cviceni/aag-cv04.pdf + // Exc. 16 + auto testcase = GENERATE ( std::make_tuple ( "0 1 0 + 1 0 1", "1", "1 0 1 0+1 1 0 1") ); -void RegExpIntegralTest::setUp() { -} - -void RegExpIntegralTest::tearDown() { -} - -void RegExpIntegralTest::testRegExpIntegral() { - // https://edux.fit.cvut.cz/oppa/BI-AAG/cviceni/aag-cv04.pdf - - // Exc. 16 - this->ExecSingleTest("0 1 0 + 1 0 1", "1", "1 0 1 0+1 1 0 1"); -} - -void RegExpIntegralTest::ExecSingleTest(std::string regexp_str, std::string string_str, std::string result) { - regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( regexp_str ); - string::LinearString < > string = factory::StringDataFactory::fromString ( "\"" + string_str + "\"" ); + const std::string & regexp_str = std::get < 0 > ( testcase ); + const std::string & string_str = std::get < 1 > ( testcase ); + const std::string & result = std::get < 2 > ( testcase ); - std::cout << factory::StringDataFactory::toString(regexp::RegExpIntegral::integral(regexp, string)) << " == " << result << std::endl; + regexp::UnboundedRegExp < > regexp = factory::StringDataFactory::fromString ( regexp_str ); + string::LinearString < > string = factory::StringDataFactory::fromString ( "\"" + string_str + "\"" ); - CPPUNIT_ASSERT(factory::StringDataFactory::toString(regexp::RegExpIntegral::integral(regexp, string)) == result); + CHECK(factory::StringDataFactory::toString(regexp::RegExpIntegral::integral(regexp, string)) == result); + } } diff --git a/alib2algo/test-src/regexp/transform/RegExpIntegralTest.h b/alib2algo/test-src/regexp/transform/RegExpIntegralTest.h deleted file mode 100644 index 9749d55503..0000000000 --- a/alib2algo/test-src/regexp/transform/RegExpIntegralTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef REGEXPINTEGRAL_TEST_H_ -#define REGEXPINTEGRAL_TEST_H_ - -#include <alib/string> - -#include <cppunit/extensions/HelperMacros.h> - -class RegExpIntegralTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( RegExpIntegralTest ); - CPPUNIT_TEST( testRegExpIntegral ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testRegExpIntegral(); - - void ExecSingleTest(std::string, std::string, std::string); -}; - -#endif /* REGEXPINTEGRAL_TEST_H_ */ diff --git a/alib2algo/test-src/string/compare/compareTest.cpp b/alib2algo/test-src/string/compare/compareTest.cpp index 409a4b87b8..06a20a2612 100644 --- a/alib2algo/test-src/string/compare/compareTest.cpp +++ b/alib2algo/test-src/string/compare/compareTest.cpp @@ -1,5 +1,4 @@ -#include <alib/list> -#include "compareTest.h" +#include <catch2/catch.hpp> #include "string/naive/ExactEqual.h" #include "string/naive/ExactCompare.h" @@ -8,64 +7,57 @@ #include "string/CyclicString.h" #include "string/Epsilon.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( compareTest, "string" ); -CPPUNIT_TEST_SUITE_REGISTRATION( compareTest ); -void compareTest::setUp() { -} +TEST_CASE ( "String Compare", "[unit][algo][string][compare]" ) { + SECTION ( "Cyclic String Equality" ) { + string::CyclicString < > str1("alfa"); + string::CyclicString < > str2("aalf"); + str2.extendAlphabet(str1.getAlphabet()); + str1.extendAlphabet(str2.getAlphabet()); -void compareTest::tearDown() { -} + CHECK(string::naive::ExactEqual::equals(str1, str2)); + } -void compareTest::testCyclicStringCompareBoolean() { - string::CyclicString < > str1("alfa"); - string::CyclicString < > str2("aalf"); - str2.extendAlphabet(str1.getAlphabet()); - str1.extendAlphabet(str2.getAlphabet()); + SECTION ( "Cyclic String integer pos" ) { + string::CyclicString < > str1("alfa"); + string::CyclicString < > str2("aalf"); + str2.extendAlphabet(str1.getAlphabet()); + str1.extendAlphabet(str2.getAlphabet()); - CPPUNIT_ASSERT(string::naive::ExactEqual::equals(str1, str2)); -} + CHECK(string::naive::ExactCompare::compare(str1, str2) == 0); -void compareTest::testCyclicStringCompareInt() { - string::CyclicString < > str1("alfa"); - string::CyclicString < > str2("aalf"); - str2.extendAlphabet(str1.getAlphabet()); - str1.extendAlphabet(str2.getAlphabet()); + string::CyclicString < > str3("ccbcccb"); + string::CyclicString < > str4("cbcccbc"); + str2.extendAlphabet(str1.getAlphabet()); + str1.extendAlphabet(str2.getAlphabet()); - CPPUNIT_ASSERT(string::naive::ExactCompare::compare(str1, str2) == 0); + CHECK(string::naive::ExactCompare::compare(str3, str4) == 0); + } - string::CyclicString < > str3("ccbcccb"); - string::CyclicString < > str4("cbcccbc"); - str2.extendAlphabet(str1.getAlphabet()); - str1.extendAlphabet(str2.getAlphabet()); + SECTION ( "Compare Cyclic" ) { + string::CyclicString < > cyclic1({DefaultSymbolType(0), DefaultSymbolType(1), DefaultSymbolType(2)}); + string::CyclicString < > cyclic2({DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(0)}); + string::CyclicString < > cyclic3({DefaultSymbolType(2), DefaultSymbolType(0), DefaultSymbolType(1)}); - CPPUNIT_ASSERT(string::naive::ExactCompare::compare(str3, str4) == 0); -} + string::CyclicString < > cyclic4({DefaultSymbolType(2), DefaultSymbolType(1), DefaultSymbolType(0)}); -void compareTest::testCompareCyclic() { - string::CyclicString < > cyclic1({DefaultSymbolType(0), DefaultSymbolType(1), DefaultSymbolType(2)}); - string::CyclicString < > cyclic2({DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(0)}); - string::CyclicString < > cyclic3({DefaultSymbolType(2), DefaultSymbolType(0), DefaultSymbolType(1)}); + string::CyclicString < > cyclic1n = string::simplify::NormalizeRotation::normalize(cyclic1); + string::CyclicString < > cyclic2n = string::simplify::NormalizeRotation::normalize(cyclic2); + string::CyclicString < > cyclic3n = string::simplify::NormalizeRotation::normalize(cyclic3); + string::CyclicString < > cyclic4n = string::simplify::NormalizeRotation::normalize(cyclic4); - string::CyclicString < > cyclic4({DefaultSymbolType(2), DefaultSymbolType(1), DefaultSymbolType(0)}); + CHECK(cyclic1 == cyclic1n); + CHECK(cyclic1n == cyclic2n); + CHECK(cyclic1n == cyclic3n); + CHECK(cyclic2n == cyclic3n); - string::CyclicString < > cyclic1n = string::simplify::NormalizeRotation::normalize(cyclic1); - string::CyclicString < > cyclic2n = string::simplify::NormalizeRotation::normalize(cyclic2); - string::CyclicString < > cyclic3n = string::simplify::NormalizeRotation::normalize(cyclic3); - string::CyclicString < > cyclic4n = string::simplify::NormalizeRotation::normalize(cyclic4); + CHECK(cyclic4n != cyclic1n); + CHECK(cyclic4n != cyclic2n); + CHECK(cyclic4n != cyclic3n); - CPPUNIT_ASSERT(cyclic1 == cyclic1n); - CPPUNIT_ASSERT(cyclic1n == cyclic2n); - CPPUNIT_ASSERT(cyclic1n == cyclic3n); - CPPUNIT_ASSERT(cyclic2n == cyclic3n); - - CPPUNIT_ASSERT(cyclic4n != cyclic1n); - CPPUNIT_ASSERT(cyclic4n != cyclic2n); - CPPUNIT_ASSERT(cyclic4n != cyclic3n); - - string::CyclicString < > cyclic5({DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(100), DefaultSymbolType(62)}); - string::CyclicString < > cyclic5n = string::simplify::NormalizeRotation::normalize(cyclic5); - string::CyclicString < > cyclic5r({DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(100)}); - CPPUNIT_ASSERT(cyclic5n == cyclic5r); + string::CyclicString < > cyclic5({DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(100), DefaultSymbolType(62)}); + string::CyclicString < > cyclic5n = string::simplify::NormalizeRotation::normalize(cyclic5); + string::CyclicString < > cyclic5r({DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(62), DefaultSymbolType(100)}); + CHECK(cyclic5n == cyclic5r); + } } - diff --git a/alib2algo/test-src/string/compare/compareTest.h b/alib2algo/test-src/string/compare/compareTest.h deleted file mode 100644 index 266e95e1d1..0000000000 --- a/alib2algo/test-src/string/compare/compareTest.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef COMPARE_TEST_H_ -#define COMPARE_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class compareTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( compareTest ); - CPPUNIT_TEST( testCyclicStringCompareBoolean ); - CPPUNIT_TEST( testCyclicStringCompareInt ); - CPPUNIT_TEST( testCompareCyclic ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testCyclicStringCompareBoolean(); - void testCyclicStringCompareInt(); - void testCompareCyclic(); -}; - -#endif // COMPARE_TEST_H_ diff --git a/alib2algo/test-src/string/properties/borderArrayTest.cpp b/alib2algo/test-src/string/properties/borderArrayTest.cpp index 42cb6f3e45..11c6ead408 100644 --- a/alib2algo/test-src/string/properties/borderArrayTest.cpp +++ b/alib2algo/test-src/string/properties/borderArrayTest.cpp @@ -1,21 +1,14 @@ -#include "borderArrayTest.h" +#include <catch2/catch.hpp> #include <string/properties/BorderArray.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( borderArrayTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION( borderArrayTest ); +TEST_CASE ( "Border Array", "[unit][algo][string][properties]" ) { + SECTION ( "Test" ) { + string::LinearString < char > string ( "alfalfaalf" ); + ext::vector<unsigned> borderArray = string::properties::BorderArray::construct(string); + ext::vector<unsigned> expected {0, 0, 0, 0, 1, 2, 3, 1, 1, 2, 3}; -void borderArrayTest::setUp() { -} - -void borderArrayTest::tearDown() { -} - -void borderArrayTest::testBorderArray() { - string::LinearString < char > string ( "alfalfaalf" ); - ext::vector<unsigned> borderArray = string::properties::BorderArray::construct(string); - ext::vector<unsigned> expected {0, 0, 0, 0, 1, 2, 3, 1, 1, 2, 3}; - - CPPUNIT_ASSERT(borderArray != expected); + CHECK(borderArray != expected); + } } diff --git a/alib2algo/test-src/string/properties/borderArrayTest.h b/alib2algo/test-src/string/properties/borderArrayTest.h deleted file mode 100644 index 6d5fcb293c..0000000000 --- a/alib2algo/test-src/string/properties/borderArrayTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef BORDER_ARRAY_TEST -#define BORDER_ARRAY_TEST - -#include <cppunit/extensions/HelperMacros.h> - -class borderArrayTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( borderArrayTest ); - CPPUNIT_TEST( testBorderArray ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testBorderArray(); -}; - -#endif // BORDER_ARRAY_TEST diff --git a/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.cpp b/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.cpp index f90e719a40..ba9bc51c51 100644 --- a/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.cpp +++ b/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.cpp @@ -1,27 +1,20 @@ -#include "ArithmeticCompressionTest.h" +#include <catch2/catch.hpp> #include <stringology/compression/ArithmeticCompression.h> #include <stringology/compression/ArithmeticDecompression.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( ArithmeticCompressionTest, "compression" ); -CPPUNIT_TEST_SUITE_REGISTRATION( ArithmeticCompressionTest ); +TEST_CASE ( "Arithmetic Compression", "[unit][algo][stringology][compression]" ) { + SECTION ( "basics" ) { + ext::string rawInput ( "abbabbabaae123456789r0 8723 babababb ab bapobababbbabaaabbafjfjdjlvldsuiueqwpomvdhgataewpvdihviasubababbba 5475 baaabba" ); + string::LinearString < char > input ( rawInput ); -void ArithmeticCompressionTest::setUp() { -} - -void ArithmeticCompressionTest::tearDown() { -} - -void ArithmeticCompressionTest::basics() { - ext::string rawInput ( "abbabbabaae123456789r0 8723 babababb ab bapobababbbabaaabbafjfjdjlvldsuiueqwpomvdhgataewpvdihviasubababbba 5475 baaabba" ); - string::LinearString < char > input ( rawInput ); - - ext::vector < bool > compressed = stringology::compression::AdaptiveIntegerArithmeticCompression::compress ( input ); - std::cout << "compressed = " << compressed << std::endl; - string::LinearString < char > output = stringology::compression::AdaptiveIntegerArithmeticDecompression::decompress ( compressed, input.getAlphabet ( ) ); + ext::vector < bool > compressed = stringology::compression::AdaptiveIntegerArithmeticCompression::compress ( input ); + INFO ( "compressed = " << compressed ); + string::LinearString < char > output = stringology::compression::AdaptiveIntegerArithmeticDecompression::decompress ( compressed, input.getAlphabet ( ) ); - std::cout << "original= " << input << std::endl << "decompressed = " << output << std::endl; - std::cout << "compressed size = " << compressed.size ( ) << std::endl << "original_size = " << input.getContent ( ).size ( ) * 8 << std::endl; - CPPUNIT_ASSERT ( input == output ); + INFO ( "original= " << input << " decompressed = " << output ); + INFO ( "compressed size = " << compressed.size ( ) << " original_size = " << input.getContent ( ).size ( ) * 8 ); + CHECK( input == output ); + } } diff --git a/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.h b/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.h deleted file mode 100644 index 13eecedb83..0000000000 --- a/alib2algo/test-src/stringology/compression/ArithmeticCompressionTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef _ARITHMETIC_COMPRESSION_TEST_H_ -#define _ARITHMETIC_COMPRESSION_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class ArithmeticCompressionTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( ArithmeticCompressionTest ); - CPPUNIT_TEST( basics ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void basics(); -}; - -#endif // _ARITHMETIC_COMPRESSION_TEST_H_ diff --git a/alib2algo/test-src/stringology/compression/LZ77Test.cpp b/alib2algo/test-src/stringology/compression/LZ77Test.cpp index 7d0d124a9e..10fa4b9e43 100644 --- a/alib2algo/test-src/stringology/compression/LZ77Test.cpp +++ b/alib2algo/test-src/stringology/compression/LZ77Test.cpp @@ -1,4 +1,4 @@ -#include "LZ77Test.h" +#include <catch2/catch.hpp> #include <string/String.h> #include <stringology/compression/LZ77Compression.h> @@ -7,105 +7,35 @@ #include <iostream> #include <tuple> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( LZ77Test, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( LZ77Test ); -void LZ77Test::setUp ( ) { -} - -void LZ77Test::tearDown ( ) { -} - -void LZ77Test::testLZ77_1 ( ) { - std::string testStr = "aabaacaaaaaababab"; - - string::LinearString < char > string = string::stringFrom ( testStr ); - std::vector < std::tuple < unsigned, unsigned, char > > res = stringology::compression::LZ77Compression::compress ( string, 6, 4 ); +TEST_CASE ( "LZ77 Compression", "[unit][algo][stringology][compression]" ) { + SECTION ( "Compress and Decompress" ) { + auto testcase = GENERATE ( + std::make_pair ( "aabaacaaaaaababab", std::vector < std::tuple < unsigned, unsigned, char > > { std::make_tuple(0, 0, 'a' ), std::make_tuple(1, 1, 'b' ), std::make_tuple(3, 2, 'c' ), std::make_tuple(3, 2, 'a' ), std::make_tuple(1, 3, 'b' ), std::make_tuple(2, 3, 'b' ) } ), + std::make_pair ( "aacaacabcabaaac", std::vector < std::tuple < unsigned, unsigned, char > > { std::make_tuple(0, 0, 'a' ), std::make_tuple(1, 1, 'c' ), std::make_tuple(3, 4, 'b' ), std::make_tuple(3, 3, 'a' ), std::make_tuple(1, 2, 'c' ) } ) ); - std::vector < std::tuple < unsigned, unsigned, char > > expectedOutput; + string::LinearString < char > string = string::stringFrom ( testcase.first ); + std::vector < std::tuple < unsigned, unsigned, char > > res = stringology::compression::LZ77Compression::compress ( string, 6, 4 ); + const std::vector < std::tuple < unsigned, unsigned, char > > & expectedOutput = testcase.second; - expectedOutput.push_back(std::make_tuple(0, 0, 'a' ) ); - expectedOutput.push_back(std::make_tuple(1, 1, 'b' ) ); - expectedOutput.push_back(std::make_tuple(3, 2, 'c' ) ); - expectedOutput.push_back(std::make_tuple(3, 2, 'a' ) ); - expectedOutput.push_back(std::make_tuple(1, 3, 'b' ) ); - expectedOutput.push_back(std::make_tuple(2, 3, 'b' ) ); - - for ( const std::tuple < unsigned, unsigned, char > & resItem : res ) - std::cout << std::get < 0 > ( resItem ) << " " << std::get < 1 > ( resItem ) << " " << std::get < 2 > ( resItem ) << std::endl; - - CPPUNIT_ASSERT ( res == expectedOutput ); - -} - -void LZ77Test::testLZ77_2 ( ) { - - std::string testStr = "aacaacabcabaaac"; - - string::LinearString < char > string = string::stringFrom ( testStr ); - std::vector < std::tuple < unsigned, unsigned, char > > res = stringology::compression::LZ77Compression::compress ( string, 6, 4 ); - - std::vector < std::tuple < unsigned, unsigned, char > > expectedOutput; - - expectedOutput.push_back(std::make_tuple(0, 0, 'a' ) ); - expectedOutput.push_back(std::make_tuple(1, 1, 'c' ) ); - expectedOutput.push_back(std::make_tuple(3, 4, 'b' ) ); - expectedOutput.push_back(std::make_tuple(3, 3, 'a' ) ); - expectedOutput.push_back(std::make_tuple(1, 2, 'c' ) ); - - for ( const std::tuple < unsigned, unsigned, char > & resItem : res ) - std::cout << std::get < 0 > ( resItem ) << " " << std::get < 1 > ( resItem ) << " " << std::get < 2 > ( resItem ) << std::endl; - - CPPUNIT_ASSERT ( res == expectedOutput ); -} - -void LZ77Test::testLZ77Decompress1 ( ) { - - std::vector < std::tuple < unsigned, unsigned, char > > input; - - input.push_back(std::make_tuple(0, 0, 'a' ) ); - input.push_back(std::make_tuple(1, 1, 'b' ) ); - input.push_back(std::make_tuple(3, 2, 'c' ) ); - input.push_back(std::make_tuple(3, 2, 'a' ) ); - input.push_back(std::make_tuple(1, 3, 'b' ) ); - input.push_back(std::make_tuple(2, 3, 'b' ) ); - - string::LinearString < char > res = stringology::compression::LZ77Decompression::decompress ( input ); - - std::string string = "aabaacaaaaaababab"; - string::LinearString < char > expectedString = string::stringFrom ( string ); - - CPPUNIT_ASSERT ( res == expectedString ); - -} - -void LZ77Test::testLZ77Decompress2 ( ) { - - std::vector < std::tuple < unsigned, unsigned, char > > input; - - input.push_back(std::make_tuple(0, 0, 'a' ) ); - input.push_back(std::make_tuple(1, 1, 'c' ) ); - input.push_back(std::make_tuple(3, 4, 'b' ) ); - input.push_back(std::make_tuple(3, 3, 'a' ) ); - input.push_back(std::make_tuple(1, 2, 'c' ) ); - - string::LinearString < char > res = stringology::compression::LZ77Decompression::decompress ( input ); - - std::string string = "aacaacabcabaaac"; - string::LinearString < char > expectedString = string::stringFrom ( string ); - - CPPUNIT_ASSERT ( res == expectedString ); - -} + /* compress */ + for ( const std::tuple < unsigned, unsigned, char > & resItem : res ) + INFO ( std::get < 0 > ( resItem ) << " " << std::get < 1 > ( resItem ) << " " << std::get < 2 > ( resItem ) ); -void LZ77Test::testLZ77Decompress3 ( ) { + CHECK ( res == expectedOutput ); - std::string string = ""; - string::LinearString < char > input = string::stringFrom ( string ); + /* decompress */ + string::LinearString < char > decompressed = stringology::compression::LZ77Decompression::decompress ( res ); + CHECK ( decompressed == string ); + } - std::vector < std::tuple < unsigned, unsigned, char > > out = stringology::compression::LZ77Compression::compress ( input, 6, 4 ); + SECTION ( "Decompress" ) { + std::string string = ""; + string::LinearString < char > input = string::stringFrom ( string ); - string::LinearString < char > res = stringology::compression::LZ77Decompression::decompress ( out ); + std::vector < std::tuple < unsigned, unsigned, char > > out = stringology::compression::LZ77Compression::compress ( input, 6, 4 ); + string::LinearString < char > res = stringology::compression::LZ77Decompression::decompress ( out ); - CPPUNIT_ASSERT ( input == res ); + CHECK ( input == res ); + } } diff --git a/alib2algo/test-src/stringology/compression/LZ77Test.h b/alib2algo/test-src/stringology/compression/LZ77Test.h deleted file mode 100644 index 823c3036b7..0000000000 --- a/alib2algo/test-src/stringology/compression/LZ77Test.h +++ /dev/null @@ -1,27 +0,0 @@ -#ifndef LZ77_TEST -#define LZ77_TEST - -#include <cppunit/extensions/HelperMacros.h> - -class LZ77Test : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( LZ77Test ); - CPPUNIT_TEST ( testLZ77_1 ); - CPPUNIT_TEST ( testLZ77_2 ); - CPPUNIT_TEST ( testLZ77Decompress1 ); - CPPUNIT_TEST ( testLZ77Decompress2 ); - CPPUNIT_TEST ( testLZ77Decompress3 ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testLZ77_1 ( ); - void testLZ77_2 ( ); - - void testLZ77Decompress1 ( ); - void testLZ77Decompress2 ( ); - void testLZ77Decompress3 ( ); -}; - -#endif // LZ77_TEST diff --git a/alib2algo/test-src/stringology/exact/stringMatchTest.cpp b/alib2algo/test-src/stringology/exact/stringMatchTest.cpp index cc261c88c9..c06196cde1 100644 --- a/alib2algo/test-src/stringology/exact/stringMatchTest.cpp +++ b/alib2algo/test-src/stringology/exact/stringMatchTest.cpp @@ -1,22 +1,13 @@ -#include <alib/list> -#include "stringMatchTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/exact/ExactFactorMatch.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( stringMatchTest, "string" ); -CPPUNIT_TEST_SUITE_REGISTRATION( stringMatchTest ); +TEST_CASE ( "Exact String Match", "[unit][algo][stringology][exact]" ) { + SECTION ( "Basic" ) { + string::LinearString < > linear1({DefaultSymbolType(0), DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(3)}); + string::LinearString < > linear2({DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(3)}); -void stringMatchTest::setUp() { + CHECK ( stringology::exact::ExactFactorMatch::match ( linear1, linear2 ).count ( 1u ) ); + } } - -void stringMatchTest::tearDown() { -} - -void stringMatchTest::testStringMatch() { - string::LinearString < > linear1({DefaultSymbolType(0), DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(3)}); - string::LinearString < > linear2({DefaultSymbolType(1), DefaultSymbolType(2), DefaultSymbolType(3)}); - - CPPUNIT_ASSERT ( stringology::exact::ExactFactorMatch::match ( linear1, linear2 ).count ( 1u ) ); -} - diff --git a/alib2algo/test-src/stringology/exact/stringMatchTest.h b/alib2algo/test-src/stringology/exact/stringMatchTest.h deleted file mode 100644 index 6af90ab70b..0000000000 --- a/alib2algo/test-src/stringology/exact/stringMatchTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef STRING_MATCH_TEST_H_ -#define STRING_MATCH_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class stringMatchTest : public CppUnit::TestFixture -{ - CPPUNIT_TEST_SUITE( stringMatchTest ); - CPPUNIT_TEST( testStringMatch ); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp(); - void tearDown(); - - void testStringMatch(); -}; - -#endif // STRING_MATCH_TEST_H_ diff --git a/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.cpp b/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.cpp index 1a76d9579e..8b809092fd 100644 --- a/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.cpp @@ -1,51 +1,41 @@ -#include "ExactSuffixAutomatonTest.h" +#include <catch2/catch.hpp> #include "string/LinearString.h" #include "stringology/indexing/ExactSuffixAutomaton.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( ExactSuffixAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( ExactSuffixAutomatonTest ); +TEST_CASE ( "Exact Suffix Automaton", "[unit][algo][stringology][indexing]" ) { + SECTION ( "Test construction" ) { -void ExactSuffixAutomatonTest::setUp ( ) { -} - -void ExactSuffixAutomatonTest::tearDown ( ) { -} - -void ExactSuffixAutomatonTest::testSuffixAutomatonConstruction ( ) { + string::LinearString < char > pattern ( "atatac" ); - string::LinearString < char > pattern ( "atatac" ); + indexes::stringology::SuffixAutomaton < char > suffixAutomaton = stringology::indexing::ExactSuffixAutomaton::construct ( pattern ); - indexes::stringology::SuffixAutomaton < char > suffixAutomaton = stringology::indexing::ExactSuffixAutomaton::construct ( pattern ); + automaton::DFA < char, unsigned > tmp ( 0 ); - automaton::DFA < char, unsigned > tmp ( 0 ); + tmp.setInputAlphabet ( pattern.getAlphabet ( ) ); - tmp.setInputAlphabet ( pattern.getAlphabet ( ) ); + for ( unsigned i = 1; i <= 6; ++i ) { + tmp.addState ( i ); + } - for ( unsigned i = 1; i <= 6; ++i ) { - tmp.addState ( i ); - } - - tmp.addFinalState ( 0 ); - tmp.addFinalState ( 6 ); + tmp.addFinalState ( 0 ); + tmp.addFinalState ( 6 ); - tmp.addTransition ( 0, 'a', 1 ); - tmp.addTransition ( 0, 't', 2 ); - tmp.addTransition ( 0, 'c', 6 ); - tmp.addTransition ( 1, 't', 2 ); - tmp.addTransition ( 1, 'c', 6 ); - tmp.addTransition ( 2, 'a', 3 ); - tmp.addTransition ( 3, 't', 4 ); - tmp.addTransition ( 3, 'c', 6 ); - tmp.addTransition ( 4, 'a', 5 ); - tmp.addTransition ( 5, 'c', 6 ); + tmp.addTransition ( 0, 'a', 1 ); + tmp.addTransition ( 0, 't', 2 ); + tmp.addTransition ( 0, 'c', 6 ); + tmp.addTransition ( 1, 't', 2 ); + tmp.addTransition ( 1, 'c', 6 ); + tmp.addTransition ( 2, 'a', 3 ); + tmp.addTransition ( 3, 't', 4 ); + tmp.addTransition ( 3, 'c', 6 ); + tmp.addTransition ( 4, 'a', 5 ); + tmp.addTransition ( 5, 'c', 6 ); - indexes::stringology::SuffixAutomaton < char > refSuffixAutomaton ( std::move ( tmp ), 6 ); + indexes::stringology::SuffixAutomaton < char > refSuffixAutomaton ( std::move ( tmp ), 6 ); - std::cout << suffixAutomaton << std::endl; - std::cout << refSuffixAutomaton << std::endl; + CHECK ( suffixAutomaton == refSuffixAutomaton ); - CPPUNIT_ASSERT ( suffixAutomaton == refSuffixAutomaton ); - - core::normalize < indexes::stringology::SuffixAutomaton < char > >::eval ( std::move ( refSuffixAutomaton ) ); + core::normalize < indexes::stringology::SuffixAutomaton < char > >::eval ( std::move ( refSuffixAutomaton ) ); + } } diff --git a/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.h b/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.h deleted file mode 100644 index eabe1ac832..0000000000 --- a/alib2algo/test-src/stringology/indexing/ExactSuffixAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef EXACT_SUFFIX_AUTOMATON_TEST_H_ -#define EXACT_SUFFIX_AUTOMATON_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class ExactSuffixAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( ExactSuffixAutomatonTest ); - CPPUNIT_TEST ( testSuffixAutomatonConstruction ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testSuffixAutomatonConstruction ( ); - -}; - -#endif // EXACT_SUFFIX_AUTOMATON_TEST_H_ diff --git a/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.cpp b/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.cpp index 8a7c184ef3..0e440e9fcd 100644 --- a/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.cpp @@ -1,47 +1,40 @@ -#include "FactorOracleAutomatonTest.h" +#include <catch2/catch.hpp> #include "string/LinearString.h" #include "stringology/indexing/ExactFactorOracleAutomaton.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( FactorOracleAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( FactorOracleAutomatonTest ); +TEST_CASE ( "Factor Oracle Automaton", "[unit][algo][stringology][indexing]" ) { + SECTION ( "Test construction" ) { + string::LinearString < char > pattern ( "atatac" ); -void FactorOracleAutomatonTest::setUp ( ) { -} - -void FactorOracleAutomatonTest::tearDown ( ) { -} + indexes::stringology::FactorOracleAutomaton < char > oracle = stringology::indexing::ExactFactorOracleAutomaton::construct ( pattern ); -void FactorOracleAutomatonTest::testFactorOracleConstruction ( ) { - string::LinearString < char > pattern ( "atatac" ); + automaton::DFA < char, unsigned > tmp ( 0 ); - indexes::stringology::FactorOracleAutomaton < char > oracle = stringology::indexing::ExactFactorOracleAutomaton::construct ( pattern ); + tmp.addFinalState ( 0 ); - automaton::DFA < char, unsigned > tmp ( 0 ); + tmp.setInputAlphabet ( pattern.getAlphabet ( ) ); - tmp.addFinalState ( 0 ); + for ( int i = 1; i <= 6; ++i ) { + tmp.addState ( i ); + tmp.addFinalState ( i ); + } - tmp.setInputAlphabet ( pattern.getAlphabet ( ) ); + tmp.addTransition ( 0, 'a', 1 ); + tmp.addTransition ( 0, 't', 2 ); + tmp.addTransition ( 0, 'c', 6 ); + tmp.addTransition ( 1, 't', 2 ); + tmp.addTransition ( 1, 'c', 6 ); + tmp.addTransition ( 2, 'a', 3 ); + tmp.addTransition ( 3, 't', 4 ); + tmp.addTransition ( 3, 'c', 6 ); + tmp.addTransition ( 4, 'a', 5 ); + tmp.addTransition ( 5, 'c', 6 ); - for ( int i = 1; i <= 6; ++i ) { - tmp.addState ( i ); - tmp.addFinalState ( i ); - } + indexes::stringology::FactorOracleAutomaton < char > refOracle ( std::move ( tmp ) ); - tmp.addTransition ( 0, 'a', 1 ); - tmp.addTransition ( 0, 't', 2 ); - tmp.addTransition ( 0, 'c', 6 ); - tmp.addTransition ( 1, 't', 2 ); - tmp.addTransition ( 1, 'c', 6 ); - tmp.addTransition ( 2, 'a', 3 ); - tmp.addTransition ( 3, 't', 4 ); - tmp.addTransition ( 3, 'c', 6 ); - tmp.addTransition ( 4, 'a', 5 ); - tmp.addTransition ( 5, 'c', 6 ); + CHECK ( oracle == refOracle ); - indexes::stringology::FactorOracleAutomaton < char > refOracle ( std::move ( tmp ) ); - - CPPUNIT_ASSERT ( oracle == refOracle ); - - core::normalize < indexes::stringology::FactorOracleAutomaton < char > >::eval ( std::move ( refOracle ) ); + core::normalize < indexes::stringology::FactorOracleAutomaton < char > >::eval ( std::move ( refOracle ) ); + } } diff --git a/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.h b/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.h deleted file mode 100644 index 3252d2be45..0000000000 --- a/alib2algo/test-src/stringology/indexing/FactorOracleAutomatonTest.h +++ /dev/null @@ -1,18 +0,0 @@ -#ifndef FACTOR_ORACLE_AUTOMATON_TEST_HPP_ -#define FACTOR_ORACLE_AUTOMATON_TEST_HPP_ - -#include <cppunit/extensions/HelperMacros.h> - -class FactorOracleAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( FactorOracleAutomatonTest ); - CPPUNIT_TEST ( testFactorOracleConstruction ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testFactorOracleConstruction ( ); -}; - -#endif // FACTOR_ORACLE_AUTOMATON_TEST_HPP_ diff --git a/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.cpp b/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.cpp index e85af2b1f0..8fb8f7d8a6 100644 --- a/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.cpp +++ b/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.cpp @@ -1,4 +1,4 @@ -#include "BackwardNondeterministicDAWGMatchingTest.h" +#include <catch2/catch.hpp> #include <string/String.h> #include <stringology/matching/WideBNDMMatcherConstruction.h> @@ -10,47 +10,39 @@ #include <string/generate/RandomStringFactory.h> #include <string/generate/RandomSubstringFactory.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( BackwardNondeterministicDAWGMatchingTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( BackwardNondeterministicDAWGMatchingTest ); - -void BackwardNondeterministicDAWGMatchingTest::setUp ( ) { -} - -void BackwardNondeterministicDAWGMatchingTest::tearDown ( ) { -} - -void BackwardNondeterministicDAWGMatchingTest::testBNDM ( ) { - - ext::vector<std::string> subjects; - ext::vector<std::string> patterns; - ext::vector<ext::set<unsigned>> expectedOccs; - - subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); - subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); - subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); - subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); - - for(size_t i = 0; i < subjects.size(); ++i) { - indexes::stringology::BitParallelIndex < char > bndmPattern1 = stringology::matching::WideBNDMMatcherConstruction::construct ( string::LinearString < char > ( patterns[i] ) ); - indexes::stringology::BitSetIndex < char > bndmPattern2 = stringology::matching::BNDMMatcherConstruction::construct ( string::LinearString < char > ( patterns[i] ) ); - ext::set < unsigned > res1 = stringology::query::WideBNDMOccurrences::query ( bndmPattern1, string::LinearString < char > ( subjects[i] ) ); - ext::set < unsigned > res2 = stringology::query::BNDMOccurrences::query ( bndmPattern2, string::LinearString < char > ( subjects[i] ) ); - CPPUNIT_ASSERT ( res1 == expectedOccs[i] ); - CPPUNIT_ASSERT ( res2 == expectedOccs[i] ); - std::cout << subjects[i] << ' ' << patterns[i] << ' ' << res1 << std::endl; +TEST_CASE ( "Backward Nondeterministic DAWG", "[unit][algo][stringology][matching]" ) { + SECTION ( "Simple" ) { + ext::vector<std::string> subjects; + ext::vector<std::string> patterns; + ext::vector<ext::set<unsigned>> expectedOccs; + + subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); + subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); + subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); + subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); + + for(size_t i = 0; i < subjects.size(); ++i) { + indexes::stringology::BitParallelIndex < char > bndmPattern1 = stringology::matching::WideBNDMMatcherConstruction::construct ( string::LinearString < char > ( patterns[i] ) ); + indexes::stringology::BitSetIndex < char > bndmPattern2 = stringology::matching::BNDMMatcherConstruction::construct ( string::LinearString < char > ( patterns[i] ) ); + ext::set < unsigned > res1 = stringology::query::WideBNDMOccurrences::query ( bndmPattern1, string::LinearString < char > ( subjects[i] ) ); + ext::set < unsigned > res2 = stringology::query::BNDMOccurrences::query ( bndmPattern2, string::LinearString < char > ( subjects[i] ) ); + CHECK ( res1 == expectedOccs[i] ); + CHECK ( res2 == expectedOccs[i] ); + INFO ( subjects[i] << ' ' << patterns[i] << ' ' << res1 ); + } + + auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64 * 64, 512, false, true); + auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 32 * 32, longSubject ); + indexes::stringology::BitSetIndex < std::string > pattern = stringology::matching::BNDMMatcherConstruction::construct ( longPattern ); + ext::set < unsigned > res = stringology::query::BNDMOccurrences::query ( pattern, longSubject ); + ext::set < unsigned > ref = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); + INFO ( "long: " << res ); + CHECK ( res == ref); } - - auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64 * 64, 512, false, true); - auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 32 * 32, longSubject ); - indexes::stringology::BitSetIndex < std::string > pattern = stringology::matching::BNDMMatcherConstruction::construct ( longPattern ); - ext::set < unsigned > res = stringology::query::BNDMOccurrences::query ( pattern, longSubject ); - ext::set < unsigned > ref = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); - std::cout << "long: " << res << std::endl; - CPPUNIT_ASSERT ( res == ref); } diff --git a/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.h b/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.h deleted file mode 100644 index 9d50ac034b..0000000000 --- a/alib2algo/test-src/stringology/matching/BackwardNondeterministicDAWGMatchingTest.h +++ /dev/null @@ -1,18 +0,0 @@ -#ifndef BACKWARD_NONDETERMINISTIC_DAWG_MATCHING_TEST_H_ -#define BACKWARD_NONDETERMINISTIC_DAWG_MATCHING_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class BackwardNondeterministicDAWGMatchingTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( BackwardNondeterministicDAWGMatchingTest ); - CPPUNIT_TEST ( testBNDM ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testBNDM ( ); -}; - -#endif // BACKWARD_NONDETERMINISTIC_DAWG_MATCHING_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.cpp index d7d3f42196..75cf2ef3b1 100644 --- a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.cpp @@ -1,186 +1,180 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/GeneralizedLevenshteinMatchingAutomaton.h> #include <automaton/FSM/EpsilonNFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "GeneralizedLevenshteinMatchingAutomatonTest.h" - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( GeneralizedLevenshteinMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( GeneralizedLevenshteinMatchingAutomatonTest ); +TEST_CASE ( "Generalized Levenshtein Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::GeneralizedLevenshteinMatchingAutomaton::construct(input_string, 2); + typedef ext::pair<unsigned int, unsigned int> State; -void GeneralizedLevenshteinMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::GeneralizedLevenshteinMatchingAutomaton::construct(input_string, 2); + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); - typedef ext::pair<unsigned int, unsigned int> State; + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + State r3 = ext::make_pair(5,1); + State r2 = ext::make_pair(5,0); + State r1 = ext::make_pair(4,0); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - State r3 = ext::make_pair(5,1); - State r2 = ext::make_pair(5,0); - State r1 = ext::make_pair(4,0); + res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'b', q5); - res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + res.addTransition(q2, 'c', q3); + res.addTransition(q5, 'c', q6); + res.addTransition(q7, 'c', q8); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'b', q5); + res.addTransition(q0, 'a', q0); // loops in initial state + res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'c', q0); + res.addTransition(q0, 'd', q0); - res.addTransition(q2, 'c', q3); - res.addTransition(q5, 'c', q6); - res.addTransition(q7, 'c', q8); + res.addTransition(q0, 'b', q4); // diagonal transitions representing replace + res.addTransition(q0, 'c', q4); + res.addTransition(q0, 'd', q4); - res.addTransition(q0, 'a', q0); // loops in initial state - res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'c', q0); - res.addTransition(q0, 'd', q0); + res.addTransition(q0, q4); // deletion - res.addTransition(q0, 'b', q4); // diagonal transitions representing replace - res.addTransition(q0, 'c', q4); - res.addTransition(q0, 'd', q4); + res.addTransition(q1, 'a', q5); + res.addTransition(q1, 'c', q5); + res.addTransition(q1, 'd', q5); + res.addTransition(q4, 'a', q7); + res.addTransition(q4, 'c', q7); + res.addTransition(q4, 'd', q7); - res.addTransition(q0, q4); // deletion + res.addTransition(q1, q5); // deletion + res.addTransition(q4, q7); - res.addTransition(q1, 'a', q5); - res.addTransition(q1, 'c', q5); - res.addTransition(q1, 'd', q5); - res.addTransition(q4, 'a', q7); - res.addTransition(q4, 'c', q7); - res.addTransition(q4, 'd', q7); + res.addTransition(q2, 'a', q6); + res.addTransition(q2, 'b', q6); + res.addTransition(q2, 'd', q6); + res.addTransition(q5, 'a', q8); + res.addTransition(q5, 'b', q8); + res.addTransition(q5, 'd', q8); - res.addTransition(q1, q5); // deletion - res.addTransition(q4, q7); + res.addTransition(q2, q6); // deletion + res.addTransition(q5, q8); - res.addTransition(q2, 'a', q6); - res.addTransition(q2, 'b', q6); - res.addTransition(q2, 'd', q6); - res.addTransition(q5, 'a', q8); - res.addTransition(q5, 'b', q8); - res.addTransition(q5, 'd', q8); + res.addTransition(q1, 'a', q4); // insertions + res.addTransition(q1, 'b', q4); + res.addTransition(q1, 'c', q4); + res.addTransition(q1, 'd', q4); - res.addTransition(q2, q6); // deletion - res.addTransition(q5, q8); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); + res.addTransition(q2, 'c', q5); + res.addTransition(q2, 'd', q5); - res.addTransition(q1, 'a', q4); // insertions - res.addTransition(q1, 'b', q4); - res.addTransition(q1, 'c', q4); - res.addTransition(q1, 'd', q4); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); + res.addTransition(q5, 'c', q7); + res.addTransition(q5, 'd', q7); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); - res.addTransition(q2, 'c', q5); - res.addTransition(q2, 'd', q5); + res.addTransition(q0, 'b', r1); // transposition + res.addTransition(r1, 'a', q5); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); - res.addTransition(q5, 'c', q7); - res.addTransition(q5, 'd', q7); + res.addTransition(q1, 'c', r2); + res.addTransition(r2, 'b', q6); - res.addTransition(q0, 'b', r1); // transposition - res.addTransition(r1, 'a', q5); + res.addTransition(q4, 'c', r3); + res.addTransition(r3, 'b', q8); - res.addTransition(q1, 'c', r2); - res.addTransition(r2, 'b', q6); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } - res.addTransition(q4, 'c', r3); - res.addTransition(r3, 'b', q8); - - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} + SECTION ( "Test Wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::GeneralizedLevenshteinMatchingAutomaton::construct(input_string, 2); -void GeneralizedLevenshteinMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::GeneralizedLevenshteinMatchingAutomaton::construct(input_string, 2); + typedef ext::pair<unsigned int, unsigned int> State; - typedef ext::pair<unsigned int, unsigned int> State; + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State r3 = ext::make_pair(5,1); + State r2 = ext::make_pair(5,0); + State r1 = ext::make_pair(4,0); - State r3 = ext::make_pair(5,1); - State r2 = ext::make_pair(5,0); - State r1 = ext::make_pair(4,0); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'a', q1); // 3 simple matching automatas - res.addTransition(q0, 'a', q1); // 3 simple matching automatas + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); + res.addTransition(q7, 'b', q8); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); - res.addTransition(q7, 'b', q8); + res.addTransition(q0, 'b', q4); // error transitions for replace - res.addTransition(q0, 'b', q4); // error transitions for replace + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q8); - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q8); + res.addTransition(q0, q4); // delete transition + res.addTransition(q1, q5); + res.addTransition(q2, q6); - res.addTransition(q0, q4); // delete transition - res.addTransition(q1, q5); - res.addTransition(q2, q6); + res.addTransition(q4, q7); + res.addTransition(q5, q8); - res.addTransition(q4, q7); - res.addTransition(q5, q8); + res.addTransition(q1, 'a', q4); // insert transitions + res.addTransition(q1, 'b', q4); - res.addTransition(q1, 'a', q4); // insert transitions - res.addTransition(q1, 'b', q4); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); + res.addTransition(q0, 'a', r1); // transpose states + res.addTransition(q0, 'b', r1); + res.addTransition(r1, 'a', q5); - res.addTransition(q0, 'a', r1); // transpose states - res.addTransition(q0, 'b', r1); - res.addTransition(r1, 'a', q5); + res.addTransition(q1, 'b', r2); + res.addTransition(r2, 'a', q6); + res.addTransition(r2, 'b', q6); - res.addTransition(q1, 'b', r2); - res.addTransition(r2, 'a', q6); - res.addTransition(r2, 'b', q6); + res.addTransition(q4, 'b', r3); + res.addTransition(r3, 'a', q8); + res.addTransition(r3, 'b', q8); - res.addTransition(q4, 'b', r3); - res.addTransition(r3, 'a', q8); - res.addTransition(r3, 'b', q8); - - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void GeneralizedLevenshteinMatchingAutomatonTest::setUp() { } - -void GeneralizedLevenshteinMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.h deleted file mode 100644 index c09ed1d87f..0000000000 --- a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef HAMMING_MATCHING_AUTOMATA_TEST_H_ -#define HAMMING_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GeneralizedLevenshteinMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(GeneralizedLevenshteinMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //HAMMING_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.cpp index 01e2aa26ae..2491838f5a 100644 --- a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.cpp @@ -1,223 +1,217 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomaton.h> #include <automaton/FSM/NFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "GeneralizedLevenshteinSequenceMatchingAutomatonTest.h" - - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( GeneralizedLevenshteinSequenceMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( GeneralizedLevenshteinSequenceMatchingAutomatonTest ); - -void GeneralizedLevenshteinSequenceMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::GeneralizedLevenshteinSequenceMatchingAutomaton::construct(input_string, 2); - - typedef ext::pair<unsigned int, unsigned int> State; +TEST_CASE ( "Generalized Levenshtein Sequence Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::GeneralizedLevenshteinSequenceMatchingAutomaton::construct(input_string, 2); - automaton::EpsilonNFA < char, void, State > test(ext::make_pair(0,0)); - test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + typedef ext::pair<unsigned int, unsigned int> State; + + automaton::EpsilonNFA < char, void, State > test(ext::make_pair(0,0)); + test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State r3 = ext::make_pair(5,1); + State r2 = ext::make_pair(5,0); + State r1 = ext::make_pair(4,0); - State r3 = ext::make_pair(5,1); - State r2 = ext::make_pair(5,0); - State r1 = ext::make_pair(4,0); + test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); + test.setFinalStates(ext::set<State> {q3, q6, q8}); - test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); - test.setFinalStates(ext::set<State> {q3, q6, q8}); + test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + test.addTransition(q1, 'b', q2); + test.addTransition(q4, 'b', q5); - test.addTransition(q1, 'b', q2); - test.addTransition(q4, 'b', q5); + test.addTransition(q2, 'c', q3); + test.addTransition(q5, 'c', q6); + test.addTransition(q7, 'c', q8); - test.addTransition(q2, 'c', q3); - test.addTransition(q5, 'c', q6); - test.addTransition(q7, 'c', q8); + test.addTransition(q0, 'a', q0); // loops in initial state + test.addTransition(q0, 'b', q0); + test.addTransition(q0, 'c', q0); + test.addTransition(q0, 'd', q0); - test.addTransition(q0, 'a', q0); // loops in initial state - test.addTransition(q0, 'b', q0); - test.addTransition(q0, 'c', q0); - test.addTransition(q0, 'd', q0); + test.addTransition(q0, 'b', q4); // diagonal transitions reptestenting replace + test.addTransition(q0, 'c', q4); + test.addTransition(q0, 'd', q4); + + test.addTransition(q0, q4); // deletion + + test.addTransition(q1, 'a', q5); + test.addTransition(q1, 'c', q5); + test.addTransition(q1, 'd', q5); + test.addTransition(q4, 'a', q7); + test.addTransition(q4, 'c', q7); + test.addTransition(q4, 'd', q7); + + test.addTransition(q1, q5); // deletion + test.addTransition(q4, q7); - test.addTransition(q0, 'b', q4); // diagonal transitions reptestenting replace - test.addTransition(q0, 'c', q4); - test.addTransition(q0, 'd', q4); + test.addTransition(q2, 'a', q6); + test.addTransition(q2, 'b', q6); + test.addTransition(q2, 'd', q6); + test.addTransition(q5, 'a', q8); + test.addTransition(q5, 'b', q8); + test.addTransition(q5, 'd', q8); - test.addTransition(q0, q4); // deletion + test.addTransition(q2, q6); // deletion + test.addTransition(q5, q8); - test.addTransition(q1, 'a', q5); - test.addTransition(q1, 'c', q5); - test.addTransition(q1, 'd', q5); - test.addTransition(q4, 'a', q7); - test.addTransition(q4, 'c', q7); - test.addTransition(q4, 'd', q7); + test.addTransition(q1, 'a', q4); // insertions + test.addTransition(q1, 'b', q4); + test.addTransition(q1, 'c', q4); + test.addTransition(q1, 'd', q4); - test.addTransition(q1, q5); // deletion - test.addTransition(q4, q7); + test.addTransition(q2, 'a', q5); + test.addTransition(q2, 'b', q5); + test.addTransition(q2, 'c', q5); + test.addTransition(q2, 'd', q5); - test.addTransition(q2, 'a', q6); - test.addTransition(q2, 'b', q6); - test.addTransition(q2, 'd', q6); - test.addTransition(q5, 'a', q8); - test.addTransition(q5, 'b', q8); - test.addTransition(q5, 'd', q8); + test.addTransition(q5, 'a', q7); + test.addTransition(q5, 'b', q7); + test.addTransition(q5, 'c', q7); + test.addTransition(q5, 'd', q7); - test.addTransition(q2, q6); // deletion - test.addTransition(q5, q8); + test.addTransition(q1, 'a', q1); // loops for sequence matching + test.addTransition(q1, 'c', q1); + test.addTransition(q1, 'd', q1); - test.addTransition(q1, 'a', q4); // insertions - test.addTransition(q1, 'b', q4); - test.addTransition(q1, 'c', q4); - test.addTransition(q1, 'd', q4); + test.addTransition(q2, 'a', q2); + test.addTransition(q2, 'b', q2); + test.addTransition(q2, 'd', q2); - test.addTransition(q2, 'a', q5); - test.addTransition(q2, 'b', q5); - test.addTransition(q2, 'c', q5); - test.addTransition(q2, 'd', q5); + test.addTransition(q4, 'a', q4); + test.addTransition(q4, 'c', q4); + test.addTransition(q4, 'd', q4); - test.addTransition(q5, 'a', q7); - test.addTransition(q5, 'b', q7); - test.addTransition(q5, 'c', q7); - test.addTransition(q5, 'd', q7); + test.addTransition(q5, 'a', q5); + test.addTransition(q5, 'b', q5); + test.addTransition(q5, 'd', q5); - test.addTransition(q1, 'a', q1); // loops for sequence matching - test.addTransition(q1, 'c', q1); - test.addTransition(q1, 'd', q1); + test.addTransition(q7, 'a', q7); + test.addTransition(q7, 'b', q7); + test.addTransition(q7, 'd', q7); - test.addTransition(q2, 'a', q2); - test.addTransition(q2, 'b', q2); - test.addTransition(q2, 'd', q2); + test.addTransition(q0, 'b', r1); // transposition + test.addTransition(r1, 'a', q5); - test.addTransition(q4, 'a', q4); - test.addTransition(q4, 'c', q4); - test.addTransition(q4, 'd', q4); + test.addTransition(q1, 'c', r2); + test.addTransition(r2, 'b', q6); - test.addTransition(q5, 'a', q5); - test.addTransition(q5, 'b', q5); - test.addTransition(q5, 'd', q5); + test.addTransition(q4, 'c', r3); + test.addTransition(r3, 'b', q8); - test.addTransition(q7, 'a', q7); - test.addTransition(q7, 'b', q7); - test.addTransition(q7, 'd', q7); + test.addTransition(r1, 'b', r1); // loops in tranposition states + test.addTransition(r1, 'c', r1); + test.addTransition(r1, 'd', r1); - test.addTransition(q0, 'b', r1); // transposition - test.addTransition(r1, 'a', q5); + test.addTransition(r2, 'a', r2); + test.addTransition(r2, 'c', r2); + test.addTransition(r2, 'd', r2); - test.addTransition(q1, 'c', r2); - test.addTransition(r2, 'b', q6); - - test.addTransition(q4, 'c', r3); - test.addTransition(r3, 'b', q8); - - test.addTransition(r1, 'b', r1); // loops in tranposition states - test.addTransition(r1, 'c', r1); - test.addTransition(r1, 'd', r1); + test.addTransition(r3, 'a', r3); + test.addTransition(r3, 'c', r3); + test.addTransition(r3, 'd', r3); - test.addTransition(r2, 'a', r2); - test.addTransition(r2, 'c', r2); - test.addTransition(r2, 'd', r2); + CHECK(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } - test.addTransition(r3, 'a', r3); - test.addTransition(r3, 'c', r3); - test.addTransition(r3, 'd', r3); + SECTION ( "Test Wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::GeneralizedLevenshteinSequenceMatchingAutomaton::construct(input_string, 2); - CPPUNIT_ASSERT(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} - -void GeneralizedLevenshteinSequenceMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::GeneralizedLevenshteinSequenceMatchingAutomaton::construct(input_string, 2); - - typedef ext::pair<unsigned int, unsigned int> State; + typedef ext::pair<unsigned int, unsigned int> State; - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State r3 = ext::make_pair(5,1); - State r2 = ext::make_pair(5,0); - State r1 = ext::make_pair(4,0); + State r3 = ext::make_pair(5,1); + State r2 = ext::make_pair(5,0); + State r1 = ext::make_pair(4,0); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8, r1, r2, r3}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q1); // 3 simple matching automatas + res.addTransition(q0, 'a', q1); // 3 simple matching automatas - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); - res.addTransition(q7, 'b', q8); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); + res.addTransition(q7, 'b', q8); - res.addTransition(q0, 'b', q4); // error transitions for replace + res.addTransition(q0, 'b', q4); // error transitions for replace - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q8); + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q8); - res.addTransition(q0, q4); // delete transition - res.addTransition(q1, q5); - res.addTransition(q2, q6); + res.addTransition(q0, q4); // delete transition + res.addTransition(q1, q5); + res.addTransition(q2, q6); - res.addTransition(q4, q7); - res.addTransition(q5, q8); + res.addTransition(q4, q7); + res.addTransition(q5, q8); - res.addTransition(q1, 'a', q4); - res.addTransition(q1, 'b', q4); + res.addTransition(q1, 'a', q4); + res.addTransition(q1, 'b', q4); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); - res.addTransition(q2, 'a', q2); // sequence matching loops - res.addTransition(q5, 'a', q5); - res.addTransition(q7, 'a', q7); + res.addTransition(q2, 'a', q2); // sequence matching loops + res.addTransition(q5, 'a', q5); + res.addTransition(q7, 'a', q7); - res.addTransition(r1, 'b', r1); + res.addTransition(r1, 'b', r1); - res.addTransition(q0, 'a', r1); // transpose states - res.addTransition(q0, 'b', r1); - res.addTransition(r1, 'a', q5); + res.addTransition(q0, 'a', r1); // transpose states + res.addTransition(q0, 'b', r1); + res.addTransition(r1, 'a', q5); - res.addTransition(q1, 'b', r2); - res.addTransition(r2, 'a', q6); - res.addTransition(r2, 'b', q6); + res.addTransition(q1, 'b', r2); + res.addTransition(r2, 'a', q6); + res.addTransition(r2, 'b', q6); - res.addTransition(q4, 'b', r3); - res.addTransition(r3, 'a', q8); - res.addTransition(r3, 'b', q8); + res.addTransition(q4, 'b', r3); + res.addTransition(r3, 'a', q8); + res.addTransition(r3, 'b', q8); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void GeneralizedLevenshteinSequenceMatchingAutomatonTest::setUp() { } - -void GeneralizedLevenshteinSequenceMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.h deleted file mode 100644 index c58d1d44d3..0000000000 --- a/alib2algo/test-src/stringology/matching/GeneralizedLevenshteinSequenceMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef GENERALIZED_LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ -#define GENERALIZED_LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GeneralizedLevenshteinSequenceMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(GeneralizedLevenshteinSequenceMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //GENERALIZED_LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.cpp index 52b05b9223..a7da2fccc9 100644 --- a/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.cpp @@ -1,118 +1,111 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/HammingMatchingAutomaton.h> #include <automaton/FSM/NFA.h> #include <string/LinearString.h> #include <string/WildcardLinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "HammingMatchingAutomatonTest.h" - - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( HammingMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( HammingMatchingAutomatonTest ); - -void HammingMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::HammingMatchingAutomaton::construct(input_string, 2); +TEST_CASE ( "Hamming Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::HammingMatchingAutomaton::construct(input_string, 2); - typedef ext::pair<unsigned int, unsigned int> State; + typedef ext::pair<unsigned int, unsigned int> State; - automaton::NFA < char, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + automaton::NFA < char, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'c', q3); - res.addTransition(q5, 'c', q6); - res.addTransition(q7, 'c', q8); + res.addTransition(q2, 'c', q3); + res.addTransition(q5, 'c', q6); + res.addTransition(q7, 'c', q8); - res.addTransition(q0, 'a', q0); // loops in initial state - res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'c', q0); - res.addTransition(q0, 'd', q0); + res.addTransition(q0, 'a', q0); // loops in initial state + res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'c', q0); + res.addTransition(q0, 'd', q0); - res.addTransition(q0, 'b', q4); // diagonal transitions representing replace - res.addTransition(q0, 'c', q4); - res.addTransition(q0, 'd', q4); + res.addTransition(q0, 'b', q4); // diagonal transitions representing replace + res.addTransition(q0, 'c', q4); + res.addTransition(q0, 'd', q4); - res.addTransition(q1, 'a', q5); - res.addTransition(q1, 'c', q5); - res.addTransition(q1, 'd', q5); - res.addTransition(q4, 'a', q7); - res.addTransition(q4, 'c', q7); - res.addTransition(q4, 'd', q7); + res.addTransition(q1, 'a', q5); + res.addTransition(q1, 'c', q5); + res.addTransition(q1, 'd', q5); + res.addTransition(q4, 'a', q7); + res.addTransition(q4, 'c', q7); + res.addTransition(q4, 'd', q7); - res.addTransition(q2, 'a', q6); - res.addTransition(q2, 'b', q6); - res.addTransition(q2, 'd', q6); - res.addTransition(q5, 'a', q8); - res.addTransition(q5, 'b', q8); - res.addTransition(q5, 'd', q8); + res.addTransition(q2, 'a', q6); + res.addTransition(q2, 'b', q6); + res.addTransition(q2, 'd', q6); + res.addTransition(q5, 'a', q8); + res.addTransition(q5, 'b', q8); + res.addTransition(q5, 'd', q8); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } -void HammingMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::HammingMatchingAutomaton::construct(input_string, 2); + SECTION ( "Test wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::HammingMatchingAutomaton::construct(input_string, 2); - typedef ext::pair<unsigned int, unsigned int> State; + typedef ext::pair<unsigned int, unsigned int> State; - automaton::NFA < char, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + automaton::NFA < char, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(3,2); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(3,2); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7}); - res.setFinalStates(ext::set<State> {q3, q6, q7}); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7}); + res.setFinalStates(ext::set<State> {q3, q6, q7}); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q1); // 3 simple matching automatas (thrid is not connected) + res.addTransition(q0, 'a', q1); // 3 simple matching automatas (thrid is not connected) - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); - res.addTransition(q0, 'b', q4); // error transitions + res.addTransition(q0, 'b', q4); // error transitions - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q7); + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q7); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - - -void HammingMatchingAutomatonTest::setUp() { } - -void HammingMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.h deleted file mode 100644 index caff8e0d7d..0000000000 --- a/alib2algo/test-src/stringology/matching/HammingMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef HAMMING_MATCHING_AUTOMATA_TEST_H_ -#define HAMMING_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class HammingMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(HammingMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //HAMMING_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.cpp index 239b5fa1ca..d171a0688f 100644 --- a/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.cpp @@ -1,138 +1,132 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/HammingSequenceMatchingAutomaton.h> #include <automaton/FSM/NFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "HammingSequenceMatchingAutomatonTest.h" - - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( HammingSequenceMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( HammingSequenceMatchingAutomatonTest ); - -void HammingSequenceMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::HammingSequenceMatchingAutomaton::construct(input_string, 2); - - typedef ext::pair<unsigned int, unsigned int> State; +TEST_CASE ( "Hamming Sequence Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::HammingSequenceMatchingAutomaton::construct(input_string, 2); - automaton::NFA < char, State > test(ext::make_pair(0,0)); - test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + typedef ext::pair<unsigned int, unsigned int> State; + + automaton::NFA < char, State > test(ext::make_pair(0,0)); + test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + test.setFinalStates(ext::set<State> {q3, q6, q8}); - test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - test.setFinalStates(ext::set<State> {q3, q6, q8}); + test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + test.addTransition(q1, 'b', q2); + test.addTransition(q4, 'b', q5); - test.addTransition(q1, 'b', q2); - test.addTransition(q4, 'b', q5); + test.addTransition(q2, 'c', q3); + test.addTransition(q5, 'c', q6); + test.addTransition(q7, 'c', q8); - test.addTransition(q2, 'c', q3); - test.addTransition(q5, 'c', q6); - test.addTransition(q7, 'c', q8); + test.addTransition(q0, 'a', q0); // loops in initial state + test.addTransition(q0, 'b', q0); + test.addTransition(q0, 'c', q0); + test.addTransition(q0, 'd', q0); - test.addTransition(q0, 'a', q0); // loops in initial state - test.addTransition(q0, 'b', q0); - test.addTransition(q0, 'c', q0); - test.addTransition(q0, 'd', q0); + test.addTransition(q0, 'b', q4); // diagonal transitions representing replace + test.addTransition(q0, 'c', q4); + test.addTransition(q0, 'd', q4); - test.addTransition(q0, 'b', q4); // diagonal transitions representing replace - test.addTransition(q0, 'c', q4); - test.addTransition(q0, 'd', q4); + test.addTransition(q1, 'a', q5); + test.addTransition(q1, 'c', q5); + test.addTransition(q1, 'd', q5); + test.addTransition(q4, 'a', q7); + test.addTransition(q4, 'c', q7); + test.addTransition(q4, 'd', q7); - test.addTransition(q1, 'a', q5); - test.addTransition(q1, 'c', q5); - test.addTransition(q1, 'd', q5); - test.addTransition(q4, 'a', q7); - test.addTransition(q4, 'c', q7); - test.addTransition(q4, 'd', q7); + test.addTransition(q2, 'a', q6); + test.addTransition(q2, 'b', q6); + test.addTransition(q2, 'd', q6); + test.addTransition(q5, 'd', q8); + test.addTransition(q5, 'a', q8); + test.addTransition(q5, 'b', q8); - test.addTransition(q2, 'a', q6); - test.addTransition(q2, 'b', q6); - test.addTransition(q2, 'd', q6); - test.addTransition(q5, 'd', q8); - test.addTransition(q5, 'a', q8); - test.addTransition(q5, 'b', q8); + test.addTransition(q1, 'a', q1); // loops for sequence matching + test.addTransition(q1, 'c', q1); + test.addTransition(q1, 'd', q1); - test.addTransition(q1, 'a', q1); // loops for sequence matching - test.addTransition(q1, 'c', q1); - test.addTransition(q1, 'd', q1); + test.addTransition(q2, 'a', q2); + test.addTransition(q2, 'b', q2); + test.addTransition(q2, 'd', q2); - test.addTransition(q2, 'a', q2); - test.addTransition(q2, 'b', q2); - test.addTransition(q2, 'd', q2); + test.addTransition(q4, 'a', q4); + test.addTransition(q4, 'c', q4); + test.addTransition(q4, 'd', q4); - test.addTransition(q4, 'a', q4); - test.addTransition(q4, 'c', q4); - test.addTransition(q4, 'd', q4); + test.addTransition(q5, 'a', q5); + test.addTransition(q5, 'b', q5); + test.addTransition(q5, 'd', q5); - test.addTransition(q5, 'a', q5); - test.addTransition(q5, 'b', q5); - test.addTransition(q5, 'd', q5); + test.addTransition(q7, 'a', q7); + test.addTransition(q7, 'b', q7); + test.addTransition(q7, 'd', q7); - test.addTransition(q7, 'a', q7); - test.addTransition(q7, 'b', q7); - test.addTransition(q7, 'd', q7); + CHECK(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } - CPPUNIT_ASSERT(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} - -void HammingSequenceMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::HammingSequenceMatchingAutomaton::construct(input_string, 2); - - typedef ext::pair<unsigned int, unsigned int> State; + SECTION ( "Test wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::HammingSequenceMatchingAutomaton::construct(input_string, 2); - automaton::NFA < char, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + typedef ext::pair<unsigned int, unsigned int> State; - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(3,2); + automaton::NFA < char, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7}); - res.setFinalStates(ext::set<State> {q3, q6, q7}); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(3,2); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7}); + res.setFinalStates(ext::set<State> {q3, q6, q7}); + + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q1); // 3 simple matching automatas (thrid is not connected) + res.addTransition(q0, 'a', q1); // 3 simple matching automatas (thrid is not connected) - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); - res.addTransition(q0, 'b', q4); // error transitions + res.addTransition(q0, 'b', q4); // error transitions - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q7); + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q7); - res.addTransition(q2, 'a', q2); // loops for sequence matching - res.addTransition(q5, 'a', q5); + res.addTransition(q2, 'a', q2); // loops for sequence matching + res.addTransition(q5, 'a', q5); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void HammingSequenceMatchingAutomatonTest::setUp() { } - -void HammingSequenceMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.h deleted file mode 100644 index c33a109a6c..0000000000 --- a/alib2algo/test-src/stringology/matching/HammingSequenceMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef HAMMING_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ -#define HAMMING_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class HammingSequenceMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(HammingSequenceMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //HAMMING_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.cpp index 4b5726e0d3..c08bc687ca 100644 --- a/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.cpp @@ -1,157 +1,151 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/LevenshteinMatchingAutomaton.h> #include <automaton/FSM/EpsilonNFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "LevenshteinMatchingAutomatonTest.h" - - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( LevenshteinMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( LevenshteinMatchingAutomatonTest ); - -void LevenshteinMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::LevenshteinMatchingAutomaton::construct(input_string, 2); +TEST_CASE ( "Levenshtein Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::LevenshteinMatchingAutomaton::construct(input_string, 2); + + typedef ext::pair<unsigned int, unsigned int> State; - typedef ext::pair<unsigned int, unsigned int> State; + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - res.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'b', q5); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'b', q5); + res.addTransition(q2, 'c', q3); + res.addTransition(q5, 'c', q6); + res.addTransition(q7, 'c', q8); - res.addTransition(q2, 'c', q3); - res.addTransition(q5, 'c', q6); - res.addTransition(q7, 'c', q8); + res.addTransition(q0, 'a', q0); // loops in initial state + res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'c', q0); + res.addTransition(q0, 'd', q0); - res.addTransition(q0, 'a', q0); // loops in initial state - res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'c', q0); - res.addTransition(q0, 'd', q0); + res.addTransition(q0, 'b', q4); // diagonal transitions representing replace + res.addTransition(q0, 'c', q4); + res.addTransition(q0, 'd', q4); - res.addTransition(q0, 'b', q4); // diagonal transitions representing replace - res.addTransition(q0, 'c', q4); - res.addTransition(q0, 'd', q4); + res.addTransition(q0, q4); // deletion - res.addTransition(q0, q4); // deletion + res.addTransition(q1, 'a', q5); + res.addTransition(q1, 'c', q5); + res.addTransition(q1, 'd', q5); + res.addTransition(q4, 'a', q7); + res.addTransition(q4, 'c', q7); + res.addTransition(q4, 'd', q7); - res.addTransition(q1, 'a', q5); - res.addTransition(q1, 'c', q5); - res.addTransition(q1, 'd', q5); - res.addTransition(q4, 'a', q7); - res.addTransition(q4, 'c', q7); - res.addTransition(q4, 'd', q7); + res.addTransition(q1, q5); // deletion + res.addTransition(q4, q7); - res.addTransition(q1, q5); // deletion - res.addTransition(q4, q7); + res.addTransition(q2, 'a', q6); + res.addTransition(q2, 'b', q6); + res.addTransition(q2, 'd', q6); + res.addTransition(q5, 'a', q8); + res.addTransition(q5, 'b', q8); + res.addTransition(q5, 'd', q8); - res.addTransition(q2, 'a', q6); - res.addTransition(q2, 'b', q6); - res.addTransition(q2, 'd', q6); - res.addTransition(q5, 'a', q8); - res.addTransition(q5, 'b', q8); - res.addTransition(q5, 'd', q8); + res.addTransition(q2, q6); // deletion + res.addTransition(q5, q8); - res.addTransition(q2, q6); // deletion - res.addTransition(q5, q8); + res.addTransition(q1, 'a', q4); // insertions + res.addTransition(q1, 'b', q4); + res.addTransition(q1, 'c', q4); + res.addTransition(q1, 'd', q4); - res.addTransition(q1, 'a', q4); // insertions - res.addTransition(q1, 'b', q4); - res.addTransition(q1, 'c', q4); - res.addTransition(q1, 'd', q4); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); + res.addTransition(q2, 'c', q5); + res.addTransition(q2, 'd', q5); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); - res.addTransition(q2, 'c', q5); - res.addTransition(q2, 'd', q5); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); + res.addTransition(q5, 'c', q7); + res.addTransition(q5, 'd', q7); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); - res.addTransition(q5, 'c', q7); - res.addTransition(q5, 'd', q7); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} - -void LevenshteinMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::LevenshteinMatchingAutomaton::construct(input_string, 2); + SECTION ( "Test wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::LevenshteinMatchingAutomaton::construct(input_string, 2); - typedef ext::pair<unsigned int, unsigned int> State; + typedef ext::pair<unsigned int, unsigned int> State; - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q1); // 3 simple matching automatas + res.addTransition(q0, 'a', q1); // 3 simple matching automatas - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); - res.addTransition(q7, 'b', q8); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); + res.addTransition(q7, 'b', q8); - res.addTransition(q0, 'b', q4); // error transitions for replace + res.addTransition(q0, 'b', q4); // error transitions for replace - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q8); + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q8); - res.addTransition(q0, q4); // delete transition - res.addTransition(q1, q5); - res.addTransition(q2, q6); + res.addTransition(q0, q4); // delete transition + res.addTransition(q1, q5); + res.addTransition(q2, q6); - res.addTransition(q4, q7); - res.addTransition(q5, q8); + res.addTransition(q4, q7); + res.addTransition(q5, q8); - res.addTransition(q1, 'a', q4); - res.addTransition(q1, 'b', q4); + res.addTransition(q1, 'a', q4); + res.addTransition(q1, 'b', q4); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void LevenshteinMatchingAutomatonTest::setUp() { } - -void LevenshteinMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.h deleted file mode 100644 index 6ec3013fa8..0000000000 --- a/alib2algo/test-src/stringology/matching/LevenshteinMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef HAMMING_MATCHING_AUTOMATA_TEST_H_ -#define HAMMING_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class LevenshteinMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(LevenshteinMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //HAMMING_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.cpp index 88bdb69167..282bd2fca4 100644 --- a/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.cpp @@ -1,181 +1,176 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/LevenshteinSequenceMatchingAutomaton.h> #include <automaton/FSM/NFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "LevenshteinSequenceMatchingAutomatonTest.h" - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( LevenshteinSequenceMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( LevenshteinSequenceMatchingAutomatonTest ); +TEST_CASE ( "Levenshtein Sequence Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::LevenshteinSequenceMatchingAutomaton::construct(input_string, 2); -void LevenshteinSequenceMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::LevenshteinSequenceMatchingAutomaton::construct(input_string, 2); + typedef ext::pair<unsigned int, unsigned int> State; - typedef ext::pair<unsigned int, unsigned int> State; + automaton::EpsilonNFA < char, void, State > test(ext::make_pair(0,0)); + test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); - automaton::EpsilonNFA < char, void, State > test(ext::make_pair(0,0)); - test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + test.setFinalStates(ext::set<State> {q3, q6, q8}); - test.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - test.setFinalStates(ext::set<State> {q3, q6, q8}); + test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) - test.addTransition(q0, 'a', q1); // vertical transitions (exact matching automata) + test.addTransition(q1, 'b', q2); + test.addTransition(q4, 'b', q5); - test.addTransition(q1, 'b', q2); - test.addTransition(q4, 'b', q5); + test.addTransition(q2, 'c', q3); + test.addTransition(q5, 'c', q6); + test.addTransition(q7, 'c', q8); - test.addTransition(q2, 'c', q3); - test.addTransition(q5, 'c', q6); - test.addTransition(q7, 'c', q8); + test.addTransition(q0, 'a', q0); // loops in initial state + test.addTransition(q0, 'b', q0); + test.addTransition(q0, 'c', q0); + test.addTransition(q0, 'd', q0); - test.addTransition(q0, 'a', q0); // loops in initial state - test.addTransition(q0, 'b', q0); - test.addTransition(q0, 'c', q0); - test.addTransition(q0, 'd', q0); + test.addTransition(q0, 'b', q4); // diagonal transitions reptestenting replace + test.addTransition(q0, 'c', q4); + test.addTransition(q0, 'd', q4); - test.addTransition(q0, 'b', q4); // diagonal transitions reptestenting replace - test.addTransition(q0, 'c', q4); - test.addTransition(q0, 'd', q4); + test.addTransition(q0, q4); // deletion - test.addTransition(q0, q4); // deletion + test.addTransition(q1, 'a', q5); + test.addTransition(q1, 'c', q5); + test.addTransition(q1, 'd', q5); + test.addTransition(q4, 'a', q7); + test.addTransition(q4, 'c', q7); + test.addTransition(q4, 'd', q7); - test.addTransition(q1, 'a', q5); - test.addTransition(q1, 'c', q5); - test.addTransition(q1, 'd', q5); - test.addTransition(q4, 'a', q7); - test.addTransition(q4, 'c', q7); - test.addTransition(q4, 'd', q7); + test.addTransition(q1, q5); // deletion + test.addTransition(q4, q7); - test.addTransition(q1, q5); // deletion - test.addTransition(q4, q7); + test.addTransition(q2, 'a', q6); + test.addTransition(q2, 'b', q6); + test.addTransition(q2, 'd', q6); + test.addTransition(q5, 'a', q8); + test.addTransition(q5, 'b', q8); + test.addTransition(q5, 'd', q8); - test.addTransition(q2, 'a', q6); - test.addTransition(q2, 'b', q6); - test.addTransition(q2, 'd', q6); - test.addTransition(q5, 'a', q8); - test.addTransition(q5, 'b', q8); - test.addTransition(q5, 'd', q8); + test.addTransition(q2, q6); // deletion + test.addTransition(q5, q8); - test.addTransition(q2, q6); // deletion - test.addTransition(q5, q8); + test.addTransition(q1, 'a', q4); // insertions + test.addTransition(q1, 'b', q4); + test.addTransition(q1, 'c', q4); + test.addTransition(q1, 'd', q4); - test.addTransition(q1, 'a', q4); // insertions - test.addTransition(q1, 'b', q4); - test.addTransition(q1, 'c', q4); - test.addTransition(q1, 'd', q4); + test.addTransition(q2, 'a', q5); + test.addTransition(q2, 'b', q5); + test.addTransition(q2, 'c', q5); + test.addTransition(q2, 'd', q5); - test.addTransition(q2, 'a', q5); - test.addTransition(q2, 'b', q5); - test.addTransition(q2, 'c', q5); - test.addTransition(q2, 'd', q5); + test.addTransition(q5, 'a', q7); + test.addTransition(q5, 'c', q7); + test.addTransition(q5, 'b', q7); + test.addTransition(q5, 'd', q7); - test.addTransition(q5, 'a', q7); - test.addTransition(q5, 'c', q7); - test.addTransition(q5, 'b', q7); - test.addTransition(q5, 'd', q7); + test.addTransition(q1, 'a', q1); // loops for sequence matching + test.addTransition(q1, 'c', q1); + test.addTransition(q1, 'd', q1); - test.addTransition(q1, 'a', q1); // loops for sequence matching - test.addTransition(q1, 'c', q1); - test.addTransition(q1, 'd', q1); + test.addTransition(q2, 'a', q2); + test.addTransition(q2, 'b', q2); + test.addTransition(q2, 'd', q2); - test.addTransition(q2, 'a', q2); - test.addTransition(q2, 'b', q2); - test.addTransition(q2, 'd', q2); + test.addTransition(q4, 'a', q4); + test.addTransition(q4, 'c', q4); + test.addTransition(q4, 'd', q4); - test.addTransition(q4, 'a', q4); - test.addTransition(q4, 'c', q4); - test.addTransition(q4, 'd', q4); + test.addTransition(q5, 'a', q5); + test.addTransition(q5, 'b', q5); + test.addTransition(q5, 'd', q5); - test.addTransition(q5, 'a', q5); - test.addTransition(q5, 'b', q5); - test.addTransition(q5, 'd', q5); + test.addTransition(q7, 'a', q7); + test.addTransition(q7, 'b', q7); + test.addTransition(q7, 'd', q7); - test.addTransition(q7, 'a', q7); - test.addTransition(q7, 'b', q7); - test.addTransition(q7, 'd', q7); - - CPPUNIT_ASSERT(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); -} + CHECK(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } -void LevenshteinSequenceMatchingAutomatonTest::testSimpleWildcardConstruction() { - ext::set<char> alphabet{'a', 'b', '@'}; - string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); - auto resulting_automata = stringology::matching::LevenshteinSequenceMatchingAutomaton::construct(input_string, 2); + SECTION ( "Test wildcard construction" ) { + ext::set<char> alphabet{'a', 'b', '@'}; + string::WildcardLinearString <char> input_string(alphabet, ext::vector<char>{'a', '@', 'b'}, '@'); + auto resulting_automata = stringology::matching::LevenshteinSequenceMatchingAutomaton::construct(input_string, 2); - typedef ext::pair<unsigned int, unsigned int> State; + typedef ext::pair<unsigned int, unsigned int> State; - automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); - res.setInputAlphabet(alphabet); + automaton::EpsilonNFA < char, void, State > res(ext::make_pair(0,0)); + res.setInputAlphabet(alphabet); - State q0 = ext::make_pair(0,0); - State q1 = ext::make_pair(1,0); - State q2 = ext::make_pair(2,0); - State q3 = ext::make_pair(3,0); - State q4 = ext::make_pair(1,1); - State q5 = ext::make_pair(2,1); - State q6 = ext::make_pair(3,1); - State q7 = ext::make_pair(2,2); - State q8 = ext::make_pair(3,2); + State q0 = ext::make_pair(0,0); + State q1 = ext::make_pair(1,0); + State q2 = ext::make_pair(2,0); + State q3 = ext::make_pair(3,0); + State q4 = ext::make_pair(1,1); + State q5 = ext::make_pair(2,1); + State q6 = ext::make_pair(3,1); + State q7 = ext::make_pair(2,2); + State q8 = ext::make_pair(3,2); - res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); - res.setFinalStates(ext::set<State> {q3, q6, q8}); + res.setStates(ext::set<State> {q0, q1, q2, q3, q4, q5, q6, q7, q8}); + res.setFinalStates(ext::set<State> {q3, q6, q8}); - res.addTransition(q0, 'a', q0); // initial loops - res.addTransition(q0, 'b', q0); + res.addTransition(q0, 'a', q0); // initial loops + res.addTransition(q0, 'b', q0); - res.addTransition(q0, 'a', q1); // 3 simple matching automatas + res.addTransition(q0, 'a', q1); // 3 simple matching automatas - res.addTransition(q1, 'a', q2); - res.addTransition(q1, 'b', q2); - res.addTransition(q4, 'a', q5); - res.addTransition(q4, 'b', q5); + res.addTransition(q1, 'a', q2); + res.addTransition(q1, 'b', q2); + res.addTransition(q4, 'a', q5); + res.addTransition(q4, 'b', q5); - res.addTransition(q2, 'b', q3); - res.addTransition(q5, 'b', q6); - res.addTransition(q7, 'b', q8); + res.addTransition(q2, 'b', q3); + res.addTransition(q5, 'b', q6); + res.addTransition(q7, 'b', q8); - res.addTransition(q0, 'b', q4); // error transitions for replace + res.addTransition(q0, 'b', q4); // error transitions for replace - res.addTransition(q2, 'a', q6); - res.addTransition(q5, 'a', q8); + res.addTransition(q2, 'a', q6); + res.addTransition(q5, 'a', q8); - res.addTransition(q0, q4); // delete transition - res.addTransition(q1, q5); - res.addTransition(q2, q6); + res.addTransition(q0, q4); // delete transition + res.addTransition(q1, q5); + res.addTransition(q2, q6); - res.addTransition(q4, q7); - res.addTransition(q5, q8); + res.addTransition(q4, q7); + res.addTransition(q5, q8); - res.addTransition(q1, 'a', q4); - res.addTransition(q1, 'b', q4); + res.addTransition(q1, 'a', q4); + res.addTransition(q1, 'b', q4); - res.addTransition(q2, 'a', q5); - res.addTransition(q2, 'b', q5); + res.addTransition(q2, 'a', q5); + res.addTransition(q2, 'b', q5); - res.addTransition(q5, 'a', q7); - res.addTransition(q5, 'b', q7); + res.addTransition(q5, 'a', q7); + res.addTransition(q5, 'b', q7); - res.addTransition(q2, 'a', q2); // sequence matching loops - res.addTransition(q5, 'a', q5); - res.addTransition(q7, 'a', q7); + res.addTransition(q2, 'a', q2); // sequence matching loops + res.addTransition(q5, 'a', q5); + res.addTransition(q7, 'a', q7); - CPPUNIT_ASSERT(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(res == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void LevenshteinSequenceMatchingAutomatonTest::setUp() { } - -void LevenshteinSequenceMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.h deleted file mode 100644 index a08b8c64ab..0000000000 --- a/alib2algo/test-src/stringology/matching/LevenshteinSequenceMatchingAutomatonTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ -#define LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class LevenshteinSequenceMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(LevenshteinSequenceMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST(testSimpleWildcardConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); - void testSimpleWildcardConstruction(); -}; -#endif //LEVENSHTEIN_SEQUENCE_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.cpp b/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.cpp index 4b02890103..4de746ad66 100644 --- a/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.cpp +++ b/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.cpp @@ -1,46 +1,40 @@ +#include <catch2/catch.hpp> + #include <stringology/matching/SequenceMatchingAutomaton.h> #include <automaton/FSM/NFA.h> #include <string/LinearString.h> #include <automaton/simplify/UnreachableStatesRemover.h> -#include "SequenceMatchingAutomatonTest.h" - - -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( SequenceMatchingAutomatonTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( SequenceMatchingAutomatonTest ); +TEST_CASE ( "Sequence Matching Automaton", "[unit][algo][stringology][matching]" ) { + SECTION ( "Test construction" ) { + ext::set<char> alphabet{'a', 'b', 'c', 'd'}; + string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); + auto resulting_automata = stringology::matching::SequenceMatchingAutomaton::construct(input_string); -void SequenceMatchingAutomatonTest::testSimpleConstruction() { - ext::set<char> alphabet{'a', 'b', 'c', 'd'}; - string::LinearString <char> input_string(alphabet, ext::vector<char>{'a', 'b', 'c'}); - auto resulting_automata = stringology::matching::SequenceMatchingAutomaton::construct(input_string); + automaton::NFA <char, unsigned int> test(0); + test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); + test.setStates(ext::set<unsigned int> {0, 1, 2, 3}); + test.addFinalState(3); - automaton::NFA <char, unsigned int> test(0); - test.setInputAlphabet(ext::set<char>{'a', 'b', 'c', 'd'}); - test.setStates(ext::set<unsigned int> {0, 1, 2, 3}); - test.addFinalState(3); + test.addTransition(0, 'a', 0); // initial loop over whole alphabet + test.addTransition(0, 'b', 0); + test.addTransition(0, 'c', 0); + test.addTransition(0, 'd', 0); - test.addTransition(0, 'a', 0); // initial loop over whole alphabet - test.addTransition(0, 'b', 0); - test.addTransition(0, 'c', 0); - test.addTransition(0, 'd', 0); + test.addTransition(0, 'a', 1); // part of a sequence - test.addTransition(0, 'a', 1); // part of a sequence + test.addTransition(1, 'a', 1); + test.addTransition(1, 'c', 1); + test.addTransition(1, 'd', 1); - test.addTransition(1, 'a', 1); - test.addTransition(1, 'c', 1); - test.addTransition(1, 'd', 1); + test.addTransition(1, 'b', 2); // part of a sequence - test.addTransition(1, 'b', 2); // part of a sequence + test.addTransition(2, 'a', 2); + test.addTransition(2, 'b', 2); + test.addTransition(2, 'd', 2); - test.addTransition(2, 'a', 2); - test.addTransition(2, 'b', 2); - test.addTransition(2, 'd', 2); + test.addTransition(2, 'c', 3); // part of a sequence - test.addTransition(2, 'c', 3); // part of a sequence - - CPPUNIT_ASSERT(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + CHECK(test == automaton::simplify::UnreachableStatesRemover::remove(resulting_automata)); + } } - -void SequenceMatchingAutomatonTest::setUp() { } - -void SequenceMatchingAutomatonTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.h b/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.h deleted file mode 100644 index cb49f2c1af..0000000000 --- a/alib2algo/test-src/stringology/matching/SequenceMatchingAutomatonTest.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef SEQUENCE_MATCHING_AUTOMATA_TEST_H_ -#define SEQUENCE_MATCHING_AUTOMATA_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class SequenceMatchingAutomatonTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(SequenceMatchingAutomatonTest); - CPPUNIT_TEST(testSimpleConstruction); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimpleConstruction(); -}; -#endif //SEQUENCE_MATCHING_AUTOMATA_TEST_H_ diff --git a/alib2algo/test-src/stringology/query/DAWGMatcherTest.cpp b/alib2algo/test-src/stringology/query/DAWGMatcherTest.cpp index 7d7e5c66e1..9864ec987e 100644 --- a/alib2algo/test-src/stringology/query/DAWGMatcherTest.cpp +++ b/alib2algo/test-src/stringology/query/DAWGMatcherTest.cpp @@ -1,4 +1,4 @@ -#include "DAWGMatcherTest.h" +#include <catch2/catch.hpp> #include "string/LinearString.h" #include "stringology/matching/DAWGMatcherConstruction.h" @@ -8,48 +8,40 @@ #include "string/generate/RandomStringFactory.h" #include "string/generate/RandomSubstringFactory.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( DAWGMatcherTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( DAWGMatcherTest ); - -void DAWGMatcherTest::setUp ( ) { -} - -void DAWGMatcherTest::tearDown ( ) { -} - -void DAWGMatcherTest::testBackwardDAWGMatching ( ) { - ext::vector<std::string> subjects; - ext::vector<std::string> patterns; - ext::vector<ext::set<unsigned>> expectedOccs; - - subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); - subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); - subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); - subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); - subjects.push_back("aaaaaaaaaa"); patterns.push_back("aa"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8}); - - - for(size_t i = 0; i < subjects.size(); ++i) { - string::LinearString < > subject ( subjects[i] ); - string::LinearString < > pattern ( patterns[i] ); - indexes::stringology::SuffixAutomaton < > suffixAutomaton = stringology::matching::DAWGMatcherConstruction::construct ( pattern ); - ext::set < unsigned > res = stringology::query::BackwardDAWGMatching::match ( subject, suffixAutomaton ); - std::cout << subjects[i] << ' ' << patterns[i] << ' ' << res << std::endl; - CPPUNIT_ASSERT ( res == expectedOccs[i] ); +TEST_CASE ( "DAWG Matcher", "[unit][algo][stringology][query]" ) { + SECTION ( "Test Backward DAWG Matching" ) { + ext::vector<std::string> subjects; + ext::vector<std::string> patterns; + ext::vector<ext::set<unsigned>> expectedOccs; + + subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); + subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); + subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); + subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); + subjects.push_back("aaaaaaaaaa"); patterns.push_back("aa"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8}); + + + for(size_t i = 0; i < subjects.size(); ++i) { + string::LinearString < > subject ( subjects[i] ); + string::LinearString < > pattern ( patterns[i] ); + indexes::stringology::SuffixAutomaton < > suffixAutomaton = stringology::matching::DAWGMatcherConstruction::construct ( pattern ); + ext::set < unsigned > res = stringology::query::BackwardDAWGMatching::match ( subject, suffixAutomaton ); + INFO ( subjects[i] << ' ' << patterns[i] << ' ' << res ); + CHECK ( res == expectedOccs[i] ); + } + + auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64, 512, false, true); + auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 5, longSubject ); + indexes::stringology::SuffixAutomaton < std::string > suffixAutomaton = stringology::matching::DAWGMatcherConstruction::construct ( longPattern ); + ext::set < unsigned > res = stringology::query::BackwardDAWGMatching::match ( longSubject, suffixAutomaton ); + ext::set < unsigned > resRef = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); + INFO ( "long: " << res ); + CHECK ( res == resRef); } - - auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64, 512, false, true); - auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 5, longSubject ); - indexes::stringology::SuffixAutomaton < std::string > suffixAutomaton = stringology::matching::DAWGMatcherConstruction::construct ( longPattern ); - ext::set < unsigned > res = stringology::query::BackwardDAWGMatching::match ( longSubject, suffixAutomaton ); - ext::set < unsigned > resRef = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); - std::cout << "long: " << res << std::endl; - CPPUNIT_ASSERT ( res == resRef); } - diff --git a/alib2algo/test-src/stringology/query/DAWGMatcherTest.h b/alib2algo/test-src/stringology/query/DAWGMatcherTest.h deleted file mode 100644 index 8241e3e7fc..0000000000 --- a/alib2algo/test-src/stringology/query/DAWGMatcherTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef SUFFIX_AUTOMATON_TEST_HPP_ -#define SUFFIX_AUTOMATON_TEST_HPP_ - -#include <cppunit/extensions/HelperMacros.h> - -class DAWGMatcherTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( DAWGMatcherTest ); - CPPUNIT_TEST ( testBackwardDAWGMatching ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testBackwardDAWGMatching ( ); - -}; - -#endif // SUFFIX_AUTOMATON_TEST_HPP_ diff --git a/alib2algo/test-src/stringology/query/OracleMatcherTest.cpp b/alib2algo/test-src/stringology/query/OracleMatcherTest.cpp index a7f3515c08..144d27ebaf 100644 --- a/alib2algo/test-src/stringology/query/OracleMatcherTest.cpp +++ b/alib2algo/test-src/stringology/query/OracleMatcherTest.cpp @@ -1,4 +1,4 @@ -#include "OracleMatcherTest.h" +#include <catch2/catch.hpp> #include "string/LinearString.h" #include "stringology/matching/OracleMatcherConstruction.h" @@ -8,46 +8,39 @@ #include "string/generate/RandomStringFactory.h" #include "string/generate/RandomSubstringFactory.h" -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( OracleMatcherTest, "stringology" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( OracleMatcherTest ); - -void OracleMatcherTest::setUp ( ) { -} - -void OracleMatcherTest::tearDown ( ) { -} - -void OracleMatcherTest::testBackwardOracleMatching ( ) { - ext::vector<std::string> subjects; - ext::vector<std::string> patterns; - ext::vector<ext::set<unsigned>> expectedOccs; - - subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); - subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); - subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); - subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); - subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); - subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); - - - for(size_t i = 0; i < subjects.size(); ++i) { - string::LinearString < > subject ( subjects[i] ); - string::LinearString < > pattern ( patterns[i] ); - automaton::DFA < DefaultSymbolType, unsigned > oracleAutomaton = stringology::matching::OracleMatcherConstruction::construct ( pattern ); - ext::set < unsigned > res = stringology::query::BackwardOracleMatching::match ( subject, oracleAutomaton ); - std::cout << subjects[i] << ' ' << patterns[i] << ' ' << res << std::endl; - CPPUNIT_ASSERT ( res == expectedOccs[i] ); +TEST_CASE ( "Oracle Matcher", "[unit][algo][stringology][query]" ) { + SECTION ( "Test Backward Oracle Matching" ) { + ext::vector<std::string> subjects; + ext::vector<std::string> patterns; + ext::vector<ext::set<unsigned>> expectedOccs; + + subjects.push_back("a"); patterns.push_back("a"); expectedOccs.push_back({0}); + subjects.push_back("a"); patterns.push_back("b"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfa"); patterns.push_back("blfalfalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfa"); patterns.push_back("alfalfalfb"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({0}); + subjects.push_back("alfalfalfaalfalfalfaabfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfa"); expectedOccs.push_back({}); + subjects.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); patterns.push_back("alfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfalfalfaalfaa"); expectedOccs.push_back({0}); + subjects.push_back("atggccttgcc"); patterns.push_back("gcc"); expectedOccs.push_back({3,8}); + subjects.push_back("aaaaaaaaaa"); patterns.push_back("a"); expectedOccs.push_back({0,1,2,3,4,5,6,7,8,9}); + + + for(size_t i = 0; i < subjects.size(); ++i) { + string::LinearString < > subject ( subjects[i] ); + string::LinearString < > pattern ( patterns[i] ); + automaton::DFA < DefaultSymbolType, unsigned > oracleAutomaton = stringology::matching::OracleMatcherConstruction::construct ( pattern ); + ext::set < unsigned > res = stringology::query::BackwardOracleMatching::match ( subject, oracleAutomaton ); + INFO ( subjects[i] << ' ' << patterns[i] << ' ' << res ); + CHECK ( res == expectedOccs[i] ); + } + + auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64, 512, false, true); + auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 5, longSubject ); + automaton::DFA < std::string, unsigned > oracleAutomaton = stringology::matching::OracleMatcherConstruction::construct ( longPattern ); + ext::set < unsigned > res = stringology::query::BackwardOracleMatching::match ( longSubject, oracleAutomaton ); + ext::set < unsigned > resRef = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); + INFO ( "long: " << res ); + CHECK ( res == resRef); } - - auto longSubject = string::generate::RandomStringFactory::generateLinearString (64 * 64, 512, false, true); - auto longPattern = string::generate::RandomSubstringFactory::generateSubstring(64 * 5, longSubject ); - automaton::DFA < std::string, unsigned > oracleAutomaton = stringology::matching::OracleMatcherConstruction::construct ( longPattern ); - ext::set < unsigned > res = stringology::query::BackwardOracleMatching::match ( longSubject, oracleAutomaton ); - ext::set < unsigned > resRef = stringology::exact::ExactFactorMatch::match ( longSubject, longPattern ); - std::cout << "long: " << res << std::endl; - CPPUNIT_ASSERT ( res == resRef); } diff --git a/alib2algo/test-src/stringology/query/OracleMatcherTest.h b/alib2algo/test-src/stringology/query/OracleMatcherTest.h deleted file mode 100644 index 886fc99358..0000000000 --- a/alib2algo/test-src/stringology/query/OracleMatcherTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef ORACLE_MATCHER_TEST_H_ -#define ORACLE_MATCHER_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class OracleMatcherTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE ( OracleMatcherTest ); - CPPUNIT_TEST ( testBackwardOracleMatching ); - CPPUNIT_TEST_SUITE_END ( ); - -public: - void setUp ( ); - void tearDown ( ); - - void testFactorOracleConstruction ( ); - void testBackwardOracleMatching ( ); -}; - -#endif // ORACLE_MATCHER_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.cpp b/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.cpp index 46ca18d388..2772a3268f 100644 --- a/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.cpp +++ b/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.cpp @@ -1,20 +1,15 @@ -#include "ExactBitParalelismTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/ExactBitParalelism.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( ExactBitParalelismTest, "bit paralelism" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( ExactBitParalelismTest ); +TEST_CASE ( "Exact Bit Parallelism", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Simple" ) { + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); -void ExactBitParalelismTest::testSimple() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); + ext::set<unsigned int> expected_result = {15}; - ext::set<unsigned int> expected_result = {15}; - - CPPUNIT_ASSERT(expected_result == stringology::simulations::ExactBitParalelism::search(text, pattern)); + CHECK(expected_result == stringology::simulations::ExactBitParalelism::search(text, pattern)); + } } - -void ExactBitParalelismTest::setUp() { } - -void ExactBitParalelismTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.h b/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.h deleted file mode 100644 index 43c1d62322..0000000000 --- a/alib2algo/test-src/stringology/simulations/ExactBitParalelismTest.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef EXACT_BIT_PARALELISM_TEST_H_ -#define EXACT_BIT_PARALELISM_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class ExactBitParalelismTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(ExactBitParalelismTest); - CPPUNIT_TEST(testSimple); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimple(); -}; -#endif // EXACT_BIT_PARALELISM_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.cpp b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.cpp index be20ec6d25..bf1ed79560 100644 --- a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.cpp +++ b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.cpp @@ -1,20 +1,15 @@ -#include "GeneralizedLevenshteinBitParalelismTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/GeneralizedLevenshteinBitParalelism.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( GeneralizedLevenshteinBitParalelismTest, "bit paralelism" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( GeneralizedLevenshteinBitParalelismTest ); +TEST_CASE ( "Generalized Levenshtein Bit Parallelism", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Simple" ) { + auto text = string::LinearString<>("adbcbaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); -void GeneralizedLevenshteinBitParalelismTest::testSimple() { - auto text = string::LinearString<>("adbcbaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::set<unsigned int> expected_result = {3, 4, 5, 6, 7, 9, 11, 12, 13, 14}; - auto result = stringology::simulations::GeneralizedLevenshteinBitParalelism::search(text, pattern, 3); - CPPUNIT_ASSERT(expected_result == result); + ext::set<unsigned int> expected_result = {3, 4, 5, 6, 7, 9, 11, 12, 13, 14}; + auto result = stringology::simulations::GeneralizedLevenshteinBitParalelism::search(text, pattern, 3); + CHECK (expected_result == result); + } } - -void GeneralizedLevenshteinBitParalelismTest::setUp() { } - -void GeneralizedLevenshteinBitParalelismTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.h b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.h deleted file mode 100644 index 3bcfe69d2d..0000000000 --- a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinBitParalelismTest.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef GENERALIZED_LEVENSHTEIN_BIT_PARALELISM_TEST_H_ -#define GENERALIZED_LEVENSHTEIN_BIT_PARALELISM_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GeneralizedLevenshteinBitParalelismTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(GeneralizedLevenshteinBitParalelismTest); - CPPUNIT_TEST(testSimple); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimple(); -}; -#endif // GENERALIZED_LEVENSHTEIN_BIT_PARALELISM_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.cpp b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.cpp index 9602ac5f9c..b8520bcff4 100644 --- a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.cpp +++ b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.cpp @@ -1,38 +1,33 @@ -#include "GeneralizedLevenshteinDynamicProgrammingTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/GeneralizedLevenshteinDynamicProgramming.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( GeneralizedLevenshteinDynamicProgrammingTest, "dynamic programming" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( GeneralizedLevenshteinDynamicProgrammingTest ); - -void GeneralizedLevenshteinDynamicProgrammingTest::testTableConstruction() { - auto text = string::LinearString<>("adbcbaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::vector<ext::vector<unsigned int>> expected_result = { - ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), - ext::vector<unsigned int>({1, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), - ext::vector<unsigned int>({2, 1, 0, 1, 2, 2, 1, 1, 1, 1, 0, 1, 2, 2, 1}), - ext::vector<unsigned int>({3, 2, 1, 0, 1, 2, 2, 2, 1, 2, 1, 0, 1, 2, 2}), - ext::vector<unsigned int>({4, 3, 2, 1, 1, 1, 2, 3, 2, 2, 2, 1, 0, 1, 2}), - ext::vector<unsigned int>({5, 4, 3, 2, 1, 1, 2, 3, 3, 3, 3, 2, 1, 0, 1}), - ext::vector<unsigned int>({6, 5, 4, 3, 2, 2, 1, 2, 4, 3, 4, 3, 2, 1, 0}), - }; - - CPPUNIT_ASSERT(expected_result == stringology::simulations::GeneralizedLevenshteinDynamicProgramming::compute_table(text, pattern)); +TEST_CASE ( "Generalized Levenshtein Dynamic Programming", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Table" ) { + auto text = string::LinearString<>("adbcbaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); + + ext::vector<ext::vector<unsigned int>> expected_result = { + ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), + ext::vector<unsigned int>({1, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), + ext::vector<unsigned int>({2, 1, 0, 1, 2, 2, 1, 1, 1, 1, 0, 1, 2, 2, 1}), + ext::vector<unsigned int>({3, 2, 1, 0, 1, 2, 2, 2, 1, 2, 1, 0, 1, 2, 2}), + ext::vector<unsigned int>({4, 3, 2, 1, 1, 1, 2, 3, 2, 2, 2, 1, 0, 1, 2}), + ext::vector<unsigned int>({5, 4, 3, 2, 1, 1, 2, 3, 3, 3, 3, 2, 1, 0, 1}), + ext::vector<unsigned int>({6, 5, 4, 3, 2, 2, 1, 2, 4, 3, 4, 3, 2, 1, 0}), + }; + + CHECK(expected_result == stringology::simulations::GeneralizedLevenshteinDynamicProgramming::compute_table(text, pattern)); + } + + SECTION ( "Occurences" ) { + auto text = string::LinearString<>("adbcbaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); + + ext::set<unsigned int> expected_result = {3, 4, 5, 6, 7, 9, 11, 12, 13, 14}; + auto result = stringology::simulations::GeneralizedLevenshteinDynamicProgramming::search(text, pattern, 3); + + CHECK(expected_result == result); + } } - -void GeneralizedLevenshteinDynamicProgrammingTest::testSearch() { - auto text = string::LinearString<>("adbcbaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::set<unsigned int> expected_result = {3, 4, 5, 6, 7, 9, 11, 12, 13, 14}; - auto result = stringology::simulations::GeneralizedLevenshteinDynamicProgramming::search(text, pattern, 3); - - CPPUNIT_ASSERT(expected_result == result); -} - -void GeneralizedLevenshteinDynamicProgrammingTest::setUp() { } - -void GeneralizedLevenshteinDynamicProgrammingTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.h b/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.h deleted file mode 100644 index 3c044661d4..0000000000 --- a/alib2algo/test-src/stringology/simulations/GeneralizedLevenshteinDynamicProgrammingTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef GENERALIZED_LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ -#define GENERALIZED_LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class GeneralizedLevenshteinDynamicProgrammingTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(GeneralizedLevenshteinDynamicProgrammingTest); - CPPUNIT_TEST(testTableConstruction); - CPPUNIT_TEST(testSearch); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testTableConstruction(); - void testSearch(); -}; -#endif // LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.cpp b/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.cpp index 60d14f2eb1..7f785986a7 100644 --- a/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.cpp +++ b/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.cpp @@ -1,20 +1,15 @@ -#include "HammingBitParalelismTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/HammingBitParalelism.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( HammingBitParalelismTest, "bit paralelism" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( HammingBitParalelismTest ); +TEST_CASE ( "Hamming Bit Parallelism", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Simple" ) { + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); -void HammingBitParalelismTest::testSimple() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::set<unsigned int> expected_result = {7,15}; - auto result = stringology::simulations::HammingBitParalelism::search(text, pattern, 3); - CPPUNIT_ASSERT(expected_result == result); + ext::set<unsigned int> expected_result = {7,15}; + auto result = stringology::simulations::HammingBitParalelism::search(text, pattern, 3); + CHECK(expected_result == result); + } } - -void HammingBitParalelismTest::setUp() { } - -void HammingBitParalelismTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.h b/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.h deleted file mode 100644 index 540acf16b4..0000000000 --- a/alib2algo/test-src/stringology/simulations/HammingBitParalelismTest.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef HAMMING_BIT_PARALELISM_TEST_H_ -#define HAMMING_BIT_PARALELISM_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class HammingBitParalelismTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(HammingBitParalelismTest); - CPPUNIT_TEST(testSimple); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimple(); -}; -#endif // HAMMING_BIT_PARALELISM_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.cpp b/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.cpp index e6f2281f9c..97dbca5b44 100644 --- a/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.cpp +++ b/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.cpp @@ -1,39 +1,33 @@ -#include "HammingDynamicProgrammingTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/HammingDynamicProgramming.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( HammingDynamicProgrammingTest, "dynamic programming" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( HammingDynamicProgrammingTest ); - -void HammingDynamicProgrammingTest::testTableConstruction() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::vector<ext::vector<unsigned int>> expected_result = { - ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), - ext::vector<unsigned int>({4, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), - ext::vector<unsigned int>({4, 5, 0, 2, 2, 1, 2, 2, 1, 1, 2, 0, 2, 2, 2, 2}), - ext::vector<unsigned int>({4, 5, 6, 1, 3, 2, 2, 3, 3, 1, 2, 3, 0, 2, 3, 3}), - ext::vector<unsigned int>({4, 5, 6, 7, 2, 3, 3, 3, 4, 3, 2, 3, 3, 0, 3, 4}), - ext::vector<unsigned int>({4, 5, 6, 6, 8, 3, 3, 4, 4, 5, 4, 3, 4, 4, 0, 4}), - ext::vector<unsigned int>({4, 4, 6, 7, 6, 9, 4, 3, 4, 5, 5, 5, 4, 5, 5, 0}), - }; - - CPPUNIT_ASSERT(expected_result == stringology::simulations::HammingDynamicProgramming::compute_table(text, pattern, 3)); -} - -void HammingDynamicProgrammingTest::testSearching() { - auto text = string::LinearString<>("patternpettannbalastpettern"); - auto pattern = string::LinearString<>("pattern"); - - auto expected_result = ext::set<unsigned int>({7, 14, 27}); - auto result = stringology::simulations::HammingDynamicProgramming::search(text, pattern, 3); - - CPPUNIT_ASSERT(expected_result == result); +TEST_CASE ( "Hamming Dynamic Programming", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Table" ) { + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); + + ext::vector<ext::vector<unsigned int>> expected_result = { + ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), + ext::vector<unsigned int>({4, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), + ext::vector<unsigned int>({4, 5, 0, 2, 2, 1, 2, 2, 1, 1, 2, 0, 2, 2, 2, 2}), + ext::vector<unsigned int>({4, 5, 6, 1, 3, 2, 2, 3, 3, 1, 2, 3, 0, 2, 3, 3}), + ext::vector<unsigned int>({4, 5, 6, 7, 2, 3, 3, 3, 4, 3, 2, 3, 3, 0, 3, 4}), + ext::vector<unsigned int>({4, 5, 6, 6, 8, 3, 3, 4, 4, 5, 4, 3, 4, 4, 0, 4}), + ext::vector<unsigned int>({4, 4, 6, 7, 6, 9, 4, 3, 4, 5, 5, 5, 4, 5, 5, 0}), + }; + + CHECK(expected_result == stringology::simulations::HammingDynamicProgramming::compute_table(text, pattern, 3)); + } + + SECTION ( "Occurences" ) { + auto text = string::LinearString<>("patternpettannbalastpettern"); + auto pattern = string::LinearString<>("pattern"); + + auto expected_result = ext::set<unsigned int>({7, 14, 27}); + auto result = stringology::simulations::HammingDynamicProgramming::search(text, pattern, 3); + + CHECK(expected_result == result); + } } - - -void HammingDynamicProgrammingTest::setUp() { } - -void HammingDynamicProgrammingTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.h b/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.h deleted file mode 100644 index 87ce0f0e4b..0000000000 --- a/alib2algo/test-src/stringology/simulations/HammingDynamicProgrammingTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef HAMMING_DYNAMIC_PROGRAMMING_TEST_H_ -#define HAMMING_DYNAMIC_PROGRAMMING_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class HammingDynamicProgrammingTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(HammingDynamicProgrammingTest); - CPPUNIT_TEST(testTableConstruction); - CPPUNIT_TEST(testSearching); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testTableConstruction(); - void testSearching(); -}; -#endif // HAMMING_DYNAMIC_PROGRAMMING_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.cpp b/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.cpp index 06db363b49..f2e774b9ae 100644 --- a/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.cpp +++ b/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.cpp @@ -1,20 +1,15 @@ -#include "LevenshteinBitParalelismTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/LevenshteinBitParalelism.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( LevenshteinBitParalelismTest, "bit paralelism" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( LevenshteinBitParalelismTest ); +TEST_CASE ( "Levenshtein Bit Parallelism", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Simple" ) { + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); -void LevenshteinBitParalelismTest::testSimple() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::set<unsigned int> expected_result = {3, 4, 6, 7, 8, 10, 12, 13, 14, 15}; - auto result = stringology::simulations::LevenshteinBitParalelism::search(text, pattern, 3); - CPPUNIT_ASSERT(expected_result == result); + ext::set<unsigned int> expected_result = {3, 4, 6, 7, 8, 10, 12, 13, 14, 15}; + auto result = stringology::simulations::LevenshteinBitParalelism::search(text, pattern, 3); + CHECK(expected_result == result); + } } - -void LevenshteinBitParalelismTest::setUp() { } - -void LevenshteinBitParalelismTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.h b/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.h deleted file mode 100644 index 89ad3fde39..0000000000 --- a/alib2algo/test-src/stringology/simulations/LevenshteinBitParalelismTest.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef LEVENSHTEIN_BIT_PARALELISM_TEST_H_ -#define LEVENSHTEIN_BIT_PARALELISM_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class LevenshteinBitParalelismTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(LevenshteinBitParalelismTest); - CPPUNIT_TEST(testSimple); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testSimple(); -}; -#endif // LEVENSHTEIN_BIT_PARALELISM_TEST_H_ diff --git a/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.cpp b/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.cpp index df2a3454a3..4a6de855ea 100644 --- a/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.cpp +++ b/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.cpp @@ -1,37 +1,33 @@ -#include "LevenshteinDynamicProgrammingTest.h" +#include <catch2/catch.hpp> #include <string/LinearString.h> #include <stringology/simulations/LevenshteinDynamicProgramming.h> -CPPUNIT_TEST_SUITE_NAMED_REGISTRATION ( LevenshteinDynamicProgrammingTest, "dynamic programming" ); -CPPUNIT_TEST_SUITE_REGISTRATION ( LevenshteinDynamicProgrammingTest ); - -void LevenshteinDynamicProgrammingTest::testTableConstruction() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::vector<ext::vector<unsigned int>> expected_result = { - ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), - ext::vector<unsigned int>({1, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), - ext::vector<unsigned int>({2, 1, 0, 1, 1, 1, 2, 1, 1, 1, 1, 0, 1, 2, 2, 1}), - ext::vector<unsigned int>({3, 2, 1, 1, 2, 1, 2, 2, 2, 1, 2, 1, 0, 1, 2, 2}), - ext::vector<unsigned int>({4, 3, 2, 2, 2, 2, 2, 3, 3, 2, 2, 2, 1, 0, 1, 2}), - ext::vector<unsigned int>({5, 4, 3, 2, 3, 3, 2, 3, 4, 3, 3, 3, 2, 1, 0, 1}), - ext::vector<unsigned int>({6, 5, 4, 3, 2, 4, 3, 2, 3, 4, 3, 4, 3, 2, 1, 0}), - }; - - CPPUNIT_ASSERT(expected_result == stringology::simulations::LevenshteinDynamicProgramming::compute_table(text, pattern)); -} - -void LevenshteinDynamicProgrammingTest::testSearch() { - auto text = string::LinearString<>("adcabcaabadbbca"); - auto pattern = string::LinearString<>("adbbca"); - - ext::set<unsigned int> expected_result = {3, 4, 6, 7, 8, 10, 12, 13, 14, 15}; - auto result = stringology::simulations::LevenshteinDynamicProgramming::search(text, pattern, 3); - CPPUNIT_ASSERT(expected_result == result); +TEST_CASE ( "Levenshtein Dynamic Programming", "[unit][algo][stringology][simulations]" ) { + SECTION ( "Table" ) { + + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); + + ext::vector<ext::vector<unsigned int>> expected_result = { + ext::vector<unsigned int>({0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}), + ext::vector<unsigned int>({1, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0}), + ext::vector<unsigned int>({2, 1, 0, 1, 1, 1, 2, 1, 1, 1, 1, 0, 1, 2, 2, 1}), + ext::vector<unsigned int>({3, 2, 1, 1, 2, 1, 2, 2, 2, 1, 2, 1, 0, 1, 2, 2}), + ext::vector<unsigned int>({4, 3, 2, 2, 2, 2, 2, 3, 3, 2, 2, 2, 1, 0, 1, 2}), + ext::vector<unsigned int>({5, 4, 3, 2, 3, 3, 2, 3, 4, 3, 3, 3, 2, 1, 0, 1}), + ext::vector<unsigned int>({6, 5, 4, 3, 2, 4, 3, 2, 3, 4, 3, 4, 3, 2, 1, 0}), + }; + + CHECK(expected_result == stringology::simulations::LevenshteinDynamicProgramming::compute_table(text, pattern)); + } + + SECTION ( "Occurences" ) { + auto text = string::LinearString<>("adcabcaabadbbca"); + auto pattern = string::LinearString<>("adbbca"); + + ext::set<unsigned int> expected_result = {3, 4, 6, 7, 8, 10, 12, 13, 14, 15}; + auto result = stringology::simulations::LevenshteinDynamicProgramming::search(text, pattern, 3); + CHECK(expected_result == result); + } } - -void LevenshteinDynamicProgrammingTest::setUp() { } - -void LevenshteinDynamicProgrammingTest::tearDown() { } diff --git a/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.h b/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.h deleted file mode 100644 index 2658bbafa6..0000000000 --- a/alib2algo/test-src/stringology/simulations/LevenshteinDynamicProgrammingTest.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ -#define LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ - -#include <cppunit/extensions/HelperMacros.h> - -class LevenshteinDynamicProgrammingTest : public CppUnit::TestFixture { - CPPUNIT_TEST_SUITE(LevenshteinDynamicProgrammingTest); - CPPUNIT_TEST(testTableConstruction); - CPPUNIT_TEST(testSearch); - CPPUNIT_TEST_SUITE_END(); - -public: - void setUp ( ); - void tearDown ( ); - - void testTableConstruction(); - void testSearch(); -}; -#endif // LEVENSHTEIN_DYNAMIC_PROGRAMMING_TEST_H_ -- GitLab