151 lines
5 KiB
C++
151 lines
5 KiB
C++
#include <ebcl/SyntaxTree.hh>
|
|
#include <cppunit/extensions/HelperMacros.h>
|
|
using namespace ebcl;
|
|
|
|
class SyntaxTreeTest : public CppUnit::TestFixture
|
|
{
|
|
CPPUNIT_TEST_SUITE( SyntaxTreeTest );
|
|
CPPUNIT_TEST( testEmpty );
|
|
CPPUNIT_TEST( testSetData );
|
|
CPPUNIT_TEST( testUpdateData );
|
|
CPPUNIT_TEST( testAddChildren );
|
|
CPPUNIT_TEST( testVisit );
|
|
CPPUNIT_TEST( testLocation );
|
|
CPPUNIT_TEST_SUITE_END( );
|
|
|
|
public:
|
|
void testEmpty( );
|
|
void testSetData( );
|
|
void testUpdateData( );
|
|
void testAddChildren( );
|
|
void testVisit( );
|
|
void testLocation( );
|
|
};
|
|
CPPUNIT_TEST_SUITE_REGISTRATION( SyntaxTreeTest );
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
enum class E_TestNode_
|
|
{
|
|
ROOT ,
|
|
ADD ,
|
|
VALUE
|
|
};
|
|
|
|
using T_Test_ = T_SyntaxTree< E_TestNode_ , uint32_t >;
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void SyntaxTreeTest::testEmpty( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
CPPUNIT_ASSERT( E_TestNode_::ROOT == st.typeOf( 0 ) );
|
|
CPPUNIT_ASSERT( st.childrenOf( 0 ).empty( ) );
|
|
CPPUNIT_ASSERT_EQUAL( 0u , st.parentOf( 0 ) );
|
|
CPPUNIT_ASSERT( !st.hasData( 0 ) );
|
|
}
|
|
|
|
void SyntaxTreeTest::testSetData( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
CPPUNIT_ASSERT( E_TestNode_::ROOT == st.typeOf( 0 ) );
|
|
CPPUNIT_ASSERT( !st.hasData( 0 ) );
|
|
CPPUNIT_ASSERT_EQUAL( 12u , st.newData< uint32_t >( 0 , 12 ) );
|
|
CPPUNIT_ASSERT( st.hasData( 0 ) );
|
|
CPPUNIT_ASSERT_EQUAL( 12u , st.dataOf< uint32_t>( 0 ) );
|
|
}
|
|
|
|
void SyntaxTreeTest::testUpdateData( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
st.newData< uint32_t >( 0 , 12 );
|
|
st.dataOf< uint32_t>( 0 ) = 42u;
|
|
CPPUNIT_ASSERT_EQUAL( 42u , st.dataOf< uint32_t>( 0 ) );
|
|
}
|
|
|
|
void SyntaxTreeTest::testAddChildren( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
const auto rc{ st.addChild( 0 , E_TestNode_::ADD ) };
|
|
CPPUNIT_ASSERT_EQUAL( 1u , rc );
|
|
CPPUNIT_ASSERT_EQUAL( 1u , st.childrenOf( 0 ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( rc , st.childrenOf( 0 )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( 0u , st.parentOf( rc ) );
|
|
CPPUNIT_ASSERT( E_TestNode_::ADD == st.typeOf( rc ) );
|
|
|
|
const auto cc{ st.addChild( rc , E_TestNode_::VALUE ) };
|
|
CPPUNIT_ASSERT_EQUAL( 2u , cc );
|
|
CPPUNIT_ASSERT_EQUAL( 1u , st.childrenOf( rc ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( cc , st.childrenOf( rc )[ 0 ] );
|
|
CPPUNIT_ASSERT( E_TestNode_::VALUE == st.typeOf( cc ) );
|
|
}
|
|
|
|
void SyntaxTreeTest::testVisit( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
const uint32_t c0{ st.addChild( 0 , E_TestNode_::ADD ) };
|
|
const uint32_t c1{ st.addChild( c0 , E_TestNode_::VALUE ) };
|
|
const uint32_t c2{ st.addChild( c0 , E_TestNode_::VALUE ) };
|
|
st.newData< uint32_t >( c1 , 12u );
|
|
st.newData< uint32_t >( c2 , 42u );
|
|
|
|
using T_Result_ = std::tuple< bool , uint32_t , T_Optional< uint32_t > >;
|
|
T_Array< T_Result_ > visitData;
|
|
st.visitor( ).visit( st.root( ) ,
|
|
[&visitData]( T_Test_::T_Node node , bool after ) {
|
|
//fprintf( stderr , "NODE %d (%c)\n" , node.node , after ? 'O' : 'I' );
|
|
visitData.add( std::make_tuple( !after , node.node ,
|
|
node.tree.hasData( node.node )
|
|
? T_Optional< uint32_t >( node.tree.dataOf< uint32_t >( node.node ) )
|
|
: T_Optional< uint32_t >() ) );
|
|
return true;
|
|
} );
|
|
|
|
// ROOT <-- ADD <-- VALUE{12}
|
|
// <-- VALUE{42}
|
|
CPPUNIT_ASSERT_EQUAL( 8u , visitData.size( ) );
|
|
|
|
CPPUNIT_ASSERT( std::get< 0 >( visitData[ 0 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 0u , std::get< 1 >( visitData[ 0 ] ) );
|
|
CPPUNIT_ASSERT( !std::get< 2 >( visitData[ 0 ] ) );
|
|
|
|
CPPUNIT_ASSERT( std::get< 0 >( visitData[ 1 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c0 , std::get< 1 >( visitData[ 1 ] ) );
|
|
CPPUNIT_ASSERT( !std::get< 2 >( visitData[ 1 ] ) );
|
|
|
|
CPPUNIT_ASSERT( std::get< 0 >( visitData[ 2 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c1 , std::get< 1 >( visitData[ 2 ] ) );
|
|
CPPUNIT_ASSERT( std::get< 2 >( visitData[ 2 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 12u , *std::get< 2 >( visitData[ 2 ] ) );
|
|
|
|
CPPUNIT_ASSERT( !std::get< 0 >( visitData[ 3 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c1 , std::get< 1 >( visitData[ 3 ] ) );
|
|
CPPUNIT_ASSERT( std::get< 2 >( visitData[ 3 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 12u , *std::get< 2 >( visitData[ 3 ] ) );
|
|
|
|
CPPUNIT_ASSERT( std::get< 0 >( visitData[ 4 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c2 , std::get< 1 >( visitData[ 4 ] ) );
|
|
CPPUNIT_ASSERT( std::get< 2 >( visitData[ 4 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 42u , *std::get< 2 >( visitData[ 4 ] ) );
|
|
|
|
CPPUNIT_ASSERT( !std::get< 0 >( visitData[ 5 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c2 , std::get< 1 >( visitData[ 5 ] ) );
|
|
CPPUNIT_ASSERT( std::get< 2 >( visitData[ 5 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 42u , *std::get< 2 >( visitData[ 5 ] ) );
|
|
|
|
CPPUNIT_ASSERT( !std::get< 0 >( visitData[ 6 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( c0 , std::get< 1 >( visitData[ 6 ] ) );
|
|
CPPUNIT_ASSERT( !std::get< 2 >( visitData[ 6 ] ) );
|
|
|
|
CPPUNIT_ASSERT( !std::get< 0 >( visitData[ 7 ] ) );
|
|
CPPUNIT_ASSERT_EQUAL( 0u , std::get< 1 >( visitData[ 7 ] ) );
|
|
CPPUNIT_ASSERT( !std::get< 2 >( visitData[ 6 ] ) );
|
|
}
|
|
|
|
void SyntaxTreeTest::testLocation( )
|
|
{
|
|
T_Test_ st{ E_TestNode_::ROOT };
|
|
CPPUNIT_ASSERT_EQUAL( 0u , st.locationOf( 0 ) );
|
|
st.locationOf( 0 ) = 123;
|
|
CPPUNIT_ASSERT_EQUAL( 123u , st.locationOf( 0 ) );
|
|
}
|