414 lines
12 KiB
C++
414 lines
12 KiB
C++
#include <ebcl/HashTables.hh>
|
|
#include <cppunit/extensions/HelperMacros.h>
|
|
using namespace ebcl;
|
|
|
|
|
|
class KeyValueTableTest : public CppUnit::TestFixture
|
|
{
|
|
CPPUNIT_TEST_SUITE( KeyValueTableTest );
|
|
CPPUNIT_TEST( testEmpty );
|
|
|
|
CPPUNIT_TEST( testAdd );
|
|
CPPUNIT_TEST( testAddDuplicate );
|
|
CPPUNIT_TEST( testUpdate );
|
|
CPPUNIT_TEST( testUpdateMissing );
|
|
CPPUNIT_TEST( testSetNew );
|
|
CPPUNIT_TEST( testSetExisting );
|
|
|
|
CPPUNIT_TEST( testRemove );
|
|
CPPUNIT_TEST( testRemoveMissing );
|
|
|
|
CPPUNIT_TEST( testContains );
|
|
CPPUNIT_TEST( testContainsMissing );
|
|
CPPUNIT_TEST( testIndexOf );
|
|
CPPUNIT_TEST( testIndexOfMissing );
|
|
CPPUNIT_TEST( testGet );
|
|
CPPUNIT_TEST( testGetMissing );
|
|
|
|
CPPUNIT_TEST( testClear );
|
|
CPPUNIT_TEST( testFree );
|
|
|
|
CPPUNIT_TEST( testCopyCons );
|
|
CPPUNIT_TEST( testCopyAss );
|
|
|
|
CPPUNIT_TEST( testMoveCons );
|
|
CPPUNIT_TEST( testMoveAss );
|
|
|
|
CPPUNIT_TEST( testSwap );
|
|
CPPUNIT_TEST_SUITE_END( );
|
|
|
|
static constexpr uint32_t C_SIZE_ = 16;
|
|
|
|
public:
|
|
void testEmpty( );
|
|
|
|
void testAdd( );
|
|
void testAddDuplicate( );
|
|
void testUpdate( );
|
|
void testUpdateMissing( );
|
|
void testSetNew( );
|
|
void testSetExisting( );
|
|
|
|
void testRemove( );
|
|
void testRemoveMissing( );
|
|
|
|
void testContains( );
|
|
void testContainsMissing( );
|
|
void testIndexOf( );
|
|
void testIndexOfMissing( );
|
|
void testGet( );
|
|
void testGetMissing( );
|
|
|
|
void testCopyCons( );
|
|
void testCopyAss( );
|
|
|
|
void testMoveCons( );
|
|
void testMoveAss( );
|
|
|
|
void testClear( );
|
|
void testFree( );
|
|
|
|
void testSwap( );
|
|
};
|
|
CPPUNIT_TEST_SUITE_REGISTRATION( KeyValueTableTest );
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testEmpty( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.values( ).size( ) );
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testAdd( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
bool ok( table.add( 123u , 456u ) );
|
|
CPPUNIT_ASSERT( ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testAddDuplicate( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.add( 123u , 456u );
|
|
bool ok( table.add( 123u , 789u ) );
|
|
CPPUNIT_ASSERT( !ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testUpdate( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.add( 123u , 456u );
|
|
bool ok( table.update( 123u , 789u ) );
|
|
CPPUNIT_ASSERT( ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 789 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testUpdateMissing( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
bool ok( table.update( 123u , 789u ) );
|
|
CPPUNIT_ASSERT( !ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.values( ).size( ) );
|
|
}
|
|
|
|
void KeyValueTableTest::testSetNew( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.set( 123u , 456u );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testSetExisting( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.add( 123u , 456u );
|
|
table.set( 123u , 789u );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 789 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testRemove( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.set( 123u , 456u );
|
|
table.set( 456u , 789u );
|
|
bool ok( table.remove( 456 ) );
|
|
CPPUNIT_ASSERT( ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testRemoveMissing( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.set( 123u , 456u );
|
|
bool ok( table.remove( 456 ) );
|
|
CPPUNIT_ASSERT( !ok );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.keys( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 1 ) , table.values( ).size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 123 ) , table.keys( )[ 0 ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , table.values( )[ 0 ] );
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testContains( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.set( 123u , 456u );
|
|
CPPUNIT_ASSERT( table.contains( 123 ) );
|
|
}
|
|
|
|
void KeyValueTableTest::testContainsMissing( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
table.set( 123u , 456u );
|
|
CPPUNIT_ASSERT( !table.contains( 456 ) );
|
|
}
|
|
|
|
void KeyValueTableTest::testIndexOf( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
|
|
const uint32_t index( table.indexOf( 57 ) );
|
|
CPPUNIT_ASSERT( index != T_HashIndex::INVALID_INDEX );
|
|
CPPUNIT_ASSERT( index < table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 114 ) , table[ index ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 114 ) , table.values( )[ index ] );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 57 ) , table.keys( )[ index ] );
|
|
}
|
|
|
|
void KeyValueTableTest::testIndexOfMissing( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
const uint32_t index( table.indexOf( 57 ) );
|
|
CPPUNIT_ASSERT( index == T_HashIndex::INVALID_INDEX );
|
|
}
|
|
|
|
void KeyValueTableTest::testGet( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
|
|
const uint32_t* index( table.get( 57 ) );
|
|
CPPUNIT_ASSERT( index != nullptr );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 114 ) , *index );
|
|
}
|
|
|
|
void KeyValueTableTest::testGetMissing( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
const uint32_t* index( table.get( 57 ) );
|
|
CPPUNIT_ASSERT( index == nullptr );
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testCopyCons( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
const auto sz( table.size( ) );
|
|
|
|
T_KeyValueTable< uint32_t , uint32_t > copy( table );
|
|
|
|
CPPUNIT_ASSERT_EQUAL( sz , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( sz , copy.size( ) );
|
|
auto const& k( table.keys( ) );
|
|
for ( uint32_t i = 0 ; i < sz ; i ++ ) {
|
|
CPPUNIT_ASSERT( copy.contains( k[ i ] ) );
|
|
|
|
const uint32_t oValue( table.values( )[ i ] );
|
|
uint32_t const* const cPtr( copy.get( k[ i ] ) );
|
|
CPPUNIT_ASSERT( cPtr != nullptr );
|
|
CPPUNIT_ASSERT_EQUAL( oValue , *cPtr );
|
|
}
|
|
}
|
|
|
|
void KeyValueTableTest::testCopyAss( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
const auto sz( table.size( ) );
|
|
|
|
T_KeyValueTable< uint32_t , uint32_t > copy;
|
|
copy = table;
|
|
|
|
CPPUNIT_ASSERT_EQUAL( sz , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( sz , copy.size( ) );
|
|
auto const& k( table.keys( ) );
|
|
for ( uint32_t i = 0 ; i < sz ; i ++ ) {
|
|
CPPUNIT_ASSERT( copy.contains( k[ i ] ) );
|
|
|
|
const uint32_t oValue( table.values( )[ i ] );
|
|
uint32_t const* const cPtr( copy.get( k[ i ] ) );
|
|
CPPUNIT_ASSERT( cPtr != nullptr );
|
|
CPPUNIT_ASSERT_EQUAL( oValue , *cPtr );
|
|
}
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testMoveCons( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
const auto sz( table.size( ) );
|
|
T_Array< uint32_t > k( table.keys( ) );
|
|
|
|
T_KeyValueTable< uint32_t , uint32_t > copy( std::move( table ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( sz , copy.size( ) );
|
|
for ( uint32_t i = 0 ; i < sz ; i ++ ) {
|
|
CPPUNIT_ASSERT( copy.contains( k[ i ] ) );
|
|
CPPUNIT_ASSERT( !table.contains( k[ i ] ) );
|
|
|
|
uint32_t const* const cPtr( copy.get( k[ i ] ) );
|
|
CPPUNIT_ASSERT( cPtr != nullptr );
|
|
CPPUNIT_ASSERT_EQUAL( k[ i ] * 2 , *cPtr );
|
|
}
|
|
}
|
|
|
|
void KeyValueTableTest::testMoveAss( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
const auto sz( table.size( ) );
|
|
T_Array< uint32_t > k( table.keys( ) );
|
|
|
|
T_KeyValueTable< uint32_t , uint32_t > copy;
|
|
copy = std::move( table );
|
|
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( sz , copy.size( ) );
|
|
for ( uint32_t i = 0 ; i < sz ; i ++ ) {
|
|
CPPUNIT_ASSERT( copy.contains( k[ i ] ) );
|
|
CPPUNIT_ASSERT( !table.contains( k[ i ] ) );
|
|
|
|
uint32_t const* const cPtr( copy.get( k[ i ] ) );
|
|
CPPUNIT_ASSERT( cPtr != nullptr );
|
|
CPPUNIT_ASSERT_EQUAL( k[ i ] * 2 , *cPtr );
|
|
}
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testClear( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
table.clear( );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
}
|
|
|
|
void KeyValueTableTest::testFree( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
for ( uint32_t i = 0 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
for ( uint32_t i = 1 ; i < 124 ; i += 2 ) {
|
|
table.set( i , i * 2 );
|
|
}
|
|
table.free( );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 0 ) , table.size( ) );
|
|
}
|
|
|
|
/*----------------------------------------------------------------------------*/
|
|
|
|
void KeyValueTableTest::testSwap( )
|
|
{
|
|
T_KeyValueTable< uint32_t , uint32_t > table;
|
|
T_KeyValueTable< uint32_t , uint32_t > table2;
|
|
for ( uint32_t i = 0 ; i < 12 ; i ++ ) {
|
|
table.set( i , i * 2 );
|
|
table2.set( 20 + i , i );
|
|
}
|
|
table.set( 123u , 456u );
|
|
|
|
swap( table , table2 );
|
|
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 12 ) , table.size( ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 13 ) , table2.size( ) );
|
|
for ( uint32_t i = 0 ; i < 12 ; i ++ ) {
|
|
CPPUNIT_ASSERT( !table.contains( i ) );
|
|
CPPUNIT_ASSERT( table.contains( 20 + i ) );
|
|
CPPUNIT_ASSERT_EQUAL( i , *( table.get( 20 + i ) ) );
|
|
|
|
CPPUNIT_ASSERT( !table2.contains( 20 + i ) );
|
|
CPPUNIT_ASSERT( table2.contains( i ) );
|
|
CPPUNIT_ASSERT_EQUAL( i * 2 , *( table2.get( i ) ) );
|
|
}
|
|
CPPUNIT_ASSERT( table2.contains( 123 ) );
|
|
CPPUNIT_ASSERT_EQUAL( uint32_t( 456 ) , *( table2.get( 123 ) ) );
|
|
}
|