430template<
typename TAllocator,
431 typename TValueDescriptor,
432 typename THash = std::hash <typename TValueDescriptor::KeyType>,
433 typename TEqual = std::equal_to<typename TValueDescriptor::KeyType>,
435 Recycling TRecycling = Recycling::Private >
440 #if ALIB_DEBUG_CRITICAL_SECTIONS
442 #define DCS ALIB_DCS_WITH(dcs)
443 #define DCSSHRD ALIB_DCS_SHARED_WITH(dcs)
454 using Element =
typename base::Element;
455 using Node =
typename base::Node;
479 using KeyType =
typename TValueDescriptor::KeyType;
513 static constexpr bool IsRecycling() {
return recyclerType::IsRecycling(); }
519 using Iterator =
typename base::template TIterator < StoredType>;
565 other.element=
nullptr;
588 other.element=
nullptr;
639 template<
bool TRequires= TRecycling!= Recycling::Shared>
643 float pBaseLoadFactor = 1.0,
644 float pMaxLoadFactor = 2.0 )
645 :
base( pAllocator, pBaseLoadFactor, pMaxLoadFactor )
663 template<
bool TRequires= TRecycling!= Recycling::Shared>
667 float pMaxLoadFactor = 2.0 )
668 :
base( pBaseLoadFactor, pMaxLoadFactor )
685 template<
typename TSharedRecycler= SharedRecyclerType>
686 requires (!std::same_as<TSharedRecycler, void>)
688 TSharedRecycler& pSharedRecycler,
689 float pBaseLoadFactor = 1.0,
690 float pMaxLoadFactor = 2.0 )
691 :
base( pAllocator, pSharedRecycler, pBaseLoadFactor, pMaxLoadFactor )
706 template<
typename TSharedRecycler= SharedRecyclerType>
707 requires (!std::same_as<TSharedRecycler, void>)
709 float pBaseLoadFactor = 1.0,
710 float pMaxLoadFactor = 2.0 )
711 :
base( pSharedRecycler, pBaseLoadFactor, pMaxLoadFactor )
726 {
return base::base::GetAllocator(); }
760 auto& allocator = base::base::GetAllocator();
762 if constexpr ( std::same_as<
typename base::recyclerType,
773 {
return base::size; }
780 {
return base::size == 0; }
793 return base::rehash(
uinteger(std::ceil( expectedSize / base::baseLoadFactor)) );
814 - base::recyclerType::Count();
815 if( requiredRecyclables > 0 )
816 recyclerType::Reserve( requiredRecyclables );
833 {DCSSHRD
return base::recyclerType::Count(); }
861 { base::baseLoadFactor= newBaseLoadFactor; }
873 {
return base::baseLoadFactor; }
897 { base::setMaxLoadFactor( newMaxLoadFactor ); }
909 {
return base::maxLoadFactor; }
921 {
return base::bucketCount; }
932 "Bucket number out of range. {}>={}", bucketNumber, base::bucketCount )
933 return uinteger(base::buckets[bucketNumber].count());
943 {
return THash{}(key) % base::bucketCount; }
955 {
return Insert( value, THash{}( TValueDescriptor().Key(
reinterpret_cast<StoredType&
>(value)) ) ); }
969 {
return Insert(value, hashCode ); }
987 auto hashCode = THash{}( TValueDescriptor().Key(
reinterpret_cast<StoredType&
>(value)) );
988 return Insert( std::move(value), hashCode );
1005 Element* element= base::allocElement(hashCode);
1008 new ( &element->value )
StoredType ( std::move(value) );
1011 base::increaseSize( 1 );
1012 auto bucketIdx= base::insertInBucket( element, hashCode );
1013 return Iterator(
this, bucketIdx, element);
1039 if( handle.IsEmpty() )
1042 base::increaseSize( 1 );
1043 Element* element= handle.element;
1044 auto hashCode= THash{}( TValueDescriptor().Key( element->value ));
1045 element->fixHashCode( hashCode );
1046 auto bucketIdx= base::insertInBucket( element, hashCode );
1047 handle.element=
nullptr;
1048 return Iterator(
this, bucketIdx, element );
1105 auto hashCode = THash{}( TValueDescriptor().Key(
reinterpret_cast<StoredType&
>(value)) );
1123 Element* element = base::allocElement( hashCode );
1125 base::increaseSize( 1 );
1126 auto bucketIdx= hashCode % base::bucketCount;
1127 base::buckets[bucketIdx].pushFront( element );
1129 new ( &element->value )
StoredType( std::move(value) );
1134 ALIB_ASSERT( it.element == element,
"MONOMEM/HASHTABLE" )
1135 while( ++it !=
cend(bucketIdx) )
1138 "InsertUnique used while element with same key-portion existed!" )
1142 return Iterator(
this, bucketIdx, element);
1162 template<
typename TRequires= MappedType>
1163 requires(!std::same_as<TRequires, StoredType>)
1189 template<
typename TRequires= MappedType>
1190 requires(!std::same_as<TRequires, StoredType>)
1192 {
return InsertOrAssign( key, std::move(mapped), THash{}(key) ); }
1216 template<
typename TRequires= MappedType>
1217 requires(!std::same_as<TRequires, StoredType>)
1220 std::pair<Iterator, bool> result= base::insertOrGet( key, hashCode );
1223 if( result.second ==
false )
1224 lang::Destruct( TValueDescriptor().Mapped( result.first.element->value ) );
1228 new (&TValueDescriptor().Key( result.first.element->value ))
KeyType( key );
1231 new ( &TValueDescriptor().Mapped( result.first.element->value ) )
MappedType( std::move( mapped) );
1253 template<
typename TRequires= MappedType>
1254 requires(!std::same_as<TRequires, StoredType>)
1280 template<
typename TRequires= MappedType>
1281 requires(!std::same_as<TRequires, StoredType>)
1285 std::pair<Iterator, bool> result= base::insertIfNotExists( key, hashCode );
1288 if( result.second ==
false )
1292 new (&TValueDescriptor().Key( result.first.element->value ))
KeyType( key );
1295 new ( &TValueDescriptor().Mapped( result.first.element->value ) )
MappedType( std::move( mapped) );
1323 template<
typename TRequires= MappedType>
1324 requires(!std::same_as<TRequires, StoredType>)
1357 auto hashCode= THash{}( TValueDescriptor().Key(value) );
1379 std::pair<Iterator, bool> result= base::insertIfNotExists( TValueDescriptor().Key(value), hashCode );
1382 if( result.second ==
false )
1386 new ( &result.first.element->value )
StoredType( std::move(value) );
1420 if( handle.IsEmpty() )
1421 return Iterator(
this, base::bucketCount,
nullptr );
1423 Element* element = handle.element;
1424 auto hashCode = THash{}( TValueDescriptor().Key( handle.element->value ) );
1425 auto bucketIdx= hashCode % base::bucketCount;
1427 Element* existing= base::findElement( hashCode, TValueDescriptor().Key( element->value ), hashCode );
1428 if ( existing !=
nullptr )
1429 return Iterator(
this, bucketIdx, existing );
1431 handle.element=
nullptr;
1432 element->fixHashCode( hashCode );
1434 bucketIdx= base::increaseSize( 1, hashCode );
1435 base::buckets[bucketIdx].pushFront( element );
1436 return Iterator(
this, bucketIdx, element);
1454 template<
typename... TArgs>
1458 Element* element= base::allocElement( 0 );
1461 new ( &element->value )
StoredType( std::forward<TArgs>(args)... );
1464 auto hashCode= THash{}( TValueDescriptor().Key( element->value ));
1465 element->fixHashCode( hashCode );
1468 base::increaseSize( 1 );
1469 auto bucketIdx= base::insertInBucket( element, hashCode );
1470 return Iterator(
this, bucketIdx, element);
1500 template<
typename... TArgs>
1504 Element* element= base::allocElement(0);
1507 new ( &element->value )
StoredType( std::forward<TArgs>(args)... );
1510 auto hashCode= THash{}( TValueDescriptor().Key( element->value ));
1511 element->fixHashCode( hashCode );
1515 auto bucketIdx= base::increaseSize( 1, hashCode );
1516 base::buckets[bucketIdx].pushFront( element );
1517 auto result=
Iterator(
this, bucketIdx, element);
1521 auto it=
ConstLocalIterator( result.bucketIdx, base::buckets[result.bucketIdx].first() );
1522 ALIB_ASSERT( it.element == result.element,
"MONOMEM/HASHTABLE" )
1524 ALIB_ASSERT_ERROR( !base::areEqual(result.element, it.element ),
"MONOMEM/HASHTABLE",
1525 "EmplaceUnique used while element with same key-portion existed!" )
1559 template<
typename TRequires=
MappedType,
typename... TArgs>
1560 requires(!std::same_as<TRequires, StoredType>)
1563 template<
typename TRequires=
MappedType,
typename... TArgs>
1564 requires(!std::same_as<TRequires, StoredType>)
1568 std::pair<Iterator, bool> result= base::insertOrGet( key, THash{}(key) );
1571 if( result.second ==
false )
1572 lang::Destruct( TValueDescriptor().Mapped( result.first.element->value ) );
1576 new (&TValueDescriptor().Key( result.first.element->value ))
KeyType( key );
1579 new ( &TValueDescriptor().Mapped( result.first.element->value ))
MappedType( std::forward<TArgs>( args)... );
1585 template<
typename TRequires=
MappedType,
typename... TArgs>
1586 requires( std::same_as<TRequires, StoredType>
1589 TArgs&&... >::value )
1593 std::pair<Iterator, bool> result= base::insertOrGet( key, THash{}(key) );
1596 if( result.second ==
false )
1600 new (&result.first.element->value)
StoredType( key, std::forward<TArgs>( args)... );
1644 template<
typename TRequires=
MappedType,
typename... TArgs>
1645 requires ( std::same_as<TRequires, StoredType>
1646 && std::is_move_constructible<StoredType>::value )
1649 StoredType value( std::forward<TArgs>( args)... );
1652 std::pair<Iterator, bool> result= base::insertIfNotExists( TValueDescriptor().Key(value),
1653 THash{}(TValueDescriptor().Key(value)) );
1656 if( result.second ==
false )
1660 new ( &result.first.element->value )
StoredType( std::move(value) );
1692 template<
typename... TArgs>
1695 template<
typename... TArgs>
1696 requires( !std::is_constructible<
StoredType,
const KeyType&, TArgs&&... >::value )
1700 std::pair<Iterator, bool> result= base::insertIfNotExists( key, THash{}(key) );
1703 if( result.second ==
false )
1707 new (&TValueDescriptor().Key(result.first.element->value))
KeyType( key );
1710 new (&TValueDescriptor().Mapped(result.first.element->value))
MappedType( std::forward<TArgs>( args)... );
1715 template<
typename... TArgs>
1716 requires(std::is_constructible<
StoredType,
const KeyType&, TArgs&&...>::value )
1720 std::pair<Iterator, bool> result= base::insertIfNotExists( key, THash{}(key) );
1723 if( result.second ==
false )
1727 new (&result.first.element->value)
StoredType( key, std::forward<TArgs>( args)... );
1755 auto hashCode = THash{}(key);
1756 auto bucketIdx= hashCode % base::bucketCount;
1757 Element* elem = base::findElement( bucketIdx, key, hashCode );
1758 return Iterator(
this, elem ==
nullptr ? base::bucketCount : bucketIdx, elem );
1769 auto hashCode = THash{}(key);
1770 auto bucketIdx= hashCode % base::bucketCount;
1771 Element* elem = base::findElement( bucketIdx, key, hashCode );
1772 return ConstIterator(
this, elem ==
nullptr ? base::bucketCount : bucketIdx, elem );
1789 auto bucketIdx= hashCode % base::bucketCount;
1790 Element* elem = base::findElement( bucketIdx, key, hashCode );
1791 return Iterator(
this, elem ==
nullptr ? base::bucketCount : bucketIdx, elem );
1808 auto bucketIdx= hashCode % base::bucketCount;
1809 Element* elem = base::findElement( bucketIdx, key, hashCode );
1810 return ConstIterator(
this, elem ==
nullptr ? base::bucketCount : bucketIdx, elem );
1821 auto hashCode= THash{}(key);
1822 return base::findElement(hashCode % base::bucketCount, key, hashCode )
1836 {DCSSHRD
return base::findRange( key ); }
1848 {DCSSHRD
return base::findRange( key ); }
1869 {
return Extract( key, THash{}(key) ); }
1887 Node* previous= base::findElementBefore( hashCode % base::bucketCount, hashCode, key );
1888 if( previous ==
nullptr )
1889 return ElementHandle(
this,
nullptr);
1891 Element* element= previous->next();
1892 previous->removeNext();
1894 return ElementHandle(
this, element );
1918 && pos.table !=
nullptr ,
1919 "MONOMEM/HASHTABLE",
"Illegal iterator." )
1921 Node* previous= base::buckets[pos.bucketIdx].findLastBefore( pos.element );
1923 "Illegal iterator: Element not found." )
1927 return ElementHandle(
this, pos.element );
1937 {
return Erase( key, THash{}(key) ); }
1953 Node* beforeFirst= base::findElementBefore( hashCode % base::bucketCount, hashCode, key );
1954 if( beforeFirst ==
nullptr )
1959 while(
end && base::areEqual(
end, key, hashCode ) )
1963 auto result= base::recyclerType::RecycleList(beforeFirst->next(),
end);
1964 beforeFirst->next(
end );
1966 base::size-= result.second;
1967 return result.second;
2003 Node* before= base::findElementBefore( hashCode % base::bucketCount, hashCode, key );
2004 if( before ==
nullptr )
2008 || !base::areEqual( before->next()->next(), key, hashCode ),
2009 "MONOMEM/HASHTABLE",
"More than one element found matching the given key" )
2011 Element* elem= before->removeNext();
2012 base::recyclerType::Recycle(elem);
2033 && pos.table !=
nullptr ,
2034 "MONOMEM/HASHTABLE",
"Illegal iterator." )
2036 Iterator result(
this, pos.bucketIdx, pos.element );
2040 Node* previous= base::buckets[pos.bucketIdx].findLastBefore( pos.element );
2042 "Illegal iterator: Element not found." )
2046 base::recyclerType::Recycle(toDelete);
2067 && start.table !=
nullptr ,
2068 "MONOMEM/HASHTABLE",
"Illegal iterator." )
2071 "Iterators are referring to different hash tables." )
2073 if( start.element ==
end.element )
2074 return Iterator(
this, start.bucketIdx, start.element );
2077 for(
uinteger bucketIdx= start.bucketIdx; bucketIdx <=
end.bucketIdx; ++bucketIdx )
2080 if( bucketIdx == base::bucketCount )
2085 if( bucketIdx == start.bucketIdx )
2088 previous= base::buckets[start.bucketIdx].findLastBefore( start.element );
2090 "Illegal iterator: Element not found." )
2094 if( base::buckets[bucketIdx].isEmpty() )
2096 previous= &base::buckets[bucketIdx];
2100 if ( bucketIdx <
end.bucketIdx )
2102 base::size-= previous->count();
2103 base::recyclerType::RecycleList( previous->next() );
2104 previous->next(
nullptr );
2108 auto pair= base::recyclerType::RecycleList(previous->next(),
end.element );
2109 previous->next(
end.element );
2110 base::size-= pair.second;
2132 ALIB_ASSERT_ERROR( pos.element !=
nullptr,
"MONOMEM/HASHTABLE",
"Illegal iterator." )
2136 Element* element= pos.element;
2137 base::buckets[pos.bucketIdx].findAndRemove( element );
2138 base::recyclerType::Recycle( element);
2157 ALIB_ASSERT_ERROR( start.element !=
nullptr,
"MONOMEM/HASHTABLE",
"Illegal iterator." )
2159 Node* previous= base::buckets[start.bucketIdx].findLastBefore( start.element );
2160 ALIB_ASSERT_ERROR( previous !=
nullptr,
"MONOMEM/HASHTABLE",
"Illegal iterator." )
2161 if( start.element ==
end.element )
2164 previous->next(
end.element );
2165 auto pair= base::recyclerType::RecycleList( start.element,
end.element );
2167 base::size-= pair.second;
2183 return Iterator (
this, base::bucketCount,
nullptr ); }
2210 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2211 return LocalIterator( bucketNumber, base::buckets[bucketNumber].first() );
2221 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2232 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2243 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2254 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2265 "Bucket number out of range: {}>={}.", bucketNumber, base::bucketCount )
2276#if ALIB_DEBUG_CONTAINERS
2298template<
typename THashtable>
2300std::tuple<double,double,integer,integer>
2303 auto qtyBuckets = hashtable.BucketCount();
2304 double averageExpected = double(hashtable.Size()) / double(qtyBuckets);
2305 uinteger minimum = std::numeric_limits<uinteger>::max();
2306 uinteger maximum = std::numeric_limits<uinteger>::min();
2309 for(
uinteger i= 0 ; i < qtyBuckets ; ++i )
2311 auto bucketSize= hashtable.BucketSize( i );
2312 sumCheck+= bucketSize;
2313 if( minimum > bucketSize ) minimum= bucketSize;
2314 if( maximum < bucketSize ) maximum= bucketSize;
2316 double diff= averageExpected - double(bucketSize);
2317 diffs+= diff > 0 ? diff : - diff;
2321 "Error: Hashtable::Size() and sum of bucket sizes differ: {}!={}", hashtable.Size(),sumCheck )
2322 double deviation= diffs / double(qtyBuckets);
2324 return std::make_tuple( averageExpected, deviation, minimum, maximum );
2370template<
typename TAllocator,
2372 typename THash = std::hash <T>,
2373 typename TEqual = std::equal_to<T>,
2375 Recycling TRecycling = Recycling::Private >
2416template<
typename TAllocator,
2419 typename THash = std::hash <TKey>,
2420 typename TEqual = std::equal_to<TKey>,
2422 Recycling TRecycling = Recycling::Private >
2432template<
typename TAllocator,
2433 typename TValueDescriptor,
2434 typename THash = std::hash <typename TValueDescriptor::KeyType>,
2435 typename TEqual = std::equal_to<typename TValueDescriptor::KeyType>,
2437 Recycling TRecycling = Recycling::Private >
2441template<
typename TAllocator,
2443 typename THash = std::hash <T>,
2444 typename TEqual = std::equal_to<T>,
2446 Recycling TRecycling = Recycling::Private >
2450template<
typename TAllocator,
2453 typename THash = std::hash <TKey>,
2454 typename TEqual = std::equal_to<TKey>,
2456 Recycling TRecycling = Recycling::Private >
2461#if ALIB_DEBUG_CRITICAL_SECTIONS
ElementHandle & operator=(const ElementHandle &other)=delete
Deleted copy assignment operator.
StoredType & Value() const
ElementHandle & operator=(ElementHandle &&other)
HashTable * table
The table we belong to.
ElementHandle(ElementHandle &other)=delete
Deleted copy constructor.
ElementHandle(HashTable *pTable, Element *pElement)
ElementHandle()
Default constructor creating and empty handle.
ElementHandle(ElementHandle &&other)
Element * element
The extracted element.
MappedType & Mapped() const
ALIB_WARNINGS_IGNORE_NOTHING_RETURNED Iterator erase(ConstIterator start, ConstIterator end)
std::pair< Iterator, bool > InsertIfNotExistent(const KeyType &key, const MappedType &mapped)
float BaseLoadFactor() const noexcept
ConstIterator end() const
Iterator EmplaceUnique(TArgs &&... args)
HashTable(AllocatorType &pAllocator, TSharedRecycler &pSharedRecycler, float pBaseLoadFactor=1.0, float pMaxLoadFactor=2.0)
std::pair< Iterator, bool > InsertIfNotExistent(const StoredType &value)
std::pair< Iterator, bool > EmplaceIfNotExistent(TArgs &&... args)
Iterator Insert(StoredType &&value, size_t hashCode)
ConstIterator cbegin() const
std::pair< Iterator, bool > EmplaceIfNotExistent(const KeyType &key, TArgs &&... args)
std::pair< ConstIterator, ConstIterator > EqualRange(const KeyType &key) const
bool EraseUnique(const KeyType &key, size_t hashCode)
bool Contains(const KeyType &key) const
ConstIterator cend() const
ConstLocalIterator begin(uinteger bucketNumber) const
void ReserveRecyclables(integer qty, lang::ValueReference reference)
static constexpr bool IsRecycling()
typename TValueDescriptor::MappedType MappedType
AllocatorType & GetAllocator() noexcept
typename base::recyclerType recyclerType
The recycler type.
Iterator Find(const KeyType &key, size_t hashCode)
Iterator Insert(ElementHandle &handle)
uinteger BucketSize(uinteger bucketNumber) const noexcept
HashTable(AllocatorType &pAllocator, float pBaseLoadFactor=1.0, float pMaxLoadFactor=2.0)
ALIB_WARNINGS_RESTORE LocalIterator erase(ConstLocalIterator pos)
integer RecyclablesCount() const noexcept
Iterator Insert(StoredType &&value)
Iterator Insert(const StoredType &value, size_t hashCode)
Iterator InsertUnique(const StoredType &value, size_t hashCode)
Iterator Find(const KeyType &key)
static constexpr bool IsCachingHashes()
Iterator Insert(const StoredType &value)
std::pair< Iterator, bool > InsertIfNotExistent(StoredType &&value, size_t hashCode)
typename base::template TLocalIterator< const StoredType > ConstLocalIterator
The constant iterator for a single bucket exposed by this container.
std::pair< Iterator, bool > InsertIfNotExistent(const KeyType &key, MappedType &&mapped)
uinteger BucketNumber(const KeyType &key) const noexcept
ConstLocalIterator cend(uinteger bucketNumber) const
typename TValueDescriptor::StoredType StoredType
TValueDescriptor DescriptorType
Type definition publishing template parameter TValueDescriptor.
std::pair< Iterator, bool > InsertOrAssign(const KeyType &key, const MappedType &mapped)
integer erase(const KeyType &key)
void BaseLoadFactor(float newBaseLoadFactor) noexcept
bool IsEmpty() const noexcept
void MaxLoadFactor(float newMaxLoadFactor) noexcept
integer Erase(const KeyType &key, size_t hashCode)
std::pair< Iterator, bool > InsertIfNotExistent(const KeyType &key, MappedType &&mapped, size_t hashCode)
std::pair< Iterator, bool > InsertOrAssign(const KeyType &key, MappedType &&mapped, size_t hashCode)
ConstIterator begin() const
std::pair< Iterator, Iterator > EqualRange(const KeyType &key)
ConstIterator Find(const KeyType &key) const
std::pair< Iterator, bool > EmplaceOrAssign(const KeyType &key, TArgs &&... args)
typename base::SharedRecyclerType SharedRecyclerType
ElementHandle Extract(const KeyType &key, size_t hashCode)
ElementHandle Extract(const KeyType &key)
TAllocator AllocatorType
Type definition publishing template parameter TAllocator.
Iterator InsertUnique(const StoredType &value)
ElementHandle Extract(ConstIterator pos)
Iterator InsertUnique(StoredType &&value)
float MaxLoadFactor() const noexcept
std::pair< Iterator, bool > InsertOrAssign(const KeyType &key, MappedType &&mapped)
ConstLocalIterator end(uinteger bucketNumber) const
LocalIterator erase(ConstLocalIterator start, ConstLocalIterator end)
THash HashType
Type definition publishing template parameter THash.
ConstIterator Find(const KeyType &key, size_t hashCode) const
typename TValueDescriptor::KeyType KeyType
LocalIterator begin(uinteger bucketNumber)
typename base::template TIterator< StoredType > Iterator
The mutable iterator exposed by this container.
std::pair< Iterator, bool > InsertIfNotExistent(StoredType &&value)
LocalIterator end(uinteger bucketNumber)
Iterator InsertUnique(StoredType &&value, size_t hashCode)
integer Size() const noexcept
typename base::template TLocalIterator< StoredType > LocalIterator
The mutable iterator for a single bucket exposed by this container.
Iterator InsertIfNotExistent(ElementHandle &handle)
TEqual EqualType
Type definition publishing template parameter TEqual.
typename base::template TIterator< const StoredType > ConstIterator
The constant iterator exposed by this container.
Iterator erase(ConstIterator pos)
ConstLocalIterator cbegin(uinteger bucketNumber) const
uinteger BucketCount() const noexcept
Iterator Emplace(TArgs &&... args)
alib::containers::HashTable< TAllocator, TIdentDescriptor< T >, THash, TEqual, THashCaching, TRecycling >< TAllocator, T, THash, TEqual, THashCaching, TRecycling >::CachedHashCodes static constexpr bool CachedHashCodes
void Reserve(integer qty, lang::ValueReference reference)
bool EraseUnique(const KeyType &key)
HashTable(TSharedRecycler &pSharedRecycler, float pBaseLoadFactor=1.0, float pMaxLoadFactor=2.0)
static constexpr Recycling RecyclingTag()
HashTable(float pBaseLoadFactor=1.0, float pMaxLoadFactor=2.0)
#define ALIB_ASSERT(cond, domain)
#define ALIB_WARNINGS_RESTORE
#define ALIB_ASSERT_ERROR(cond, domain,...)
#define ALIB_WARNINGS_IGNORE_NOTHING_RETURNED
#define ALIB_DEBUG_CRITICAL_SECTIONS
std::tuple< double, double, integer, integer > DbgGetHashTableDistribution(const THashtable &hashtable)
HashTable< TAllocator, TPairDescriptor< TKey, TMapped >, THash, TEqual, THashCaching, TRecycling > HashMap
HashTable< TAllocator, TIdentDescriptor< T >, THash, TEqual, THashCaching, TRecycling > HashSet
Caching
Denotes if a cache mechanism is enabled or disabled.
ValueReference
Denotes if a value is interpreted as an absolute or relative number.
@ Relative
Referring to a relative value.
@ Absolute
Referring to an absolute value.
containers::HashSet< TAllocator, T, THash, TEqual, THashCaching, TRecycling > HashSet
Type alias in namespace alib. See type definition alib::containers::HashSet.
containers::HashTable< TAllocator, TValueDescriptor, THash, TEqual, THashCaching, TRecycling > HashTable
Type alias in namespace alib. See type definition alib::containers::HashSet.
lang::integer integer
Type alias in namespace alib.
containers::HashMap< TAllocator, TKey, TMapped, THash, TEqual, THashCaching, TRecycling > HashMap
Type alias in namespace alib.
containers::Recycling Recycling
Type alias in namespace alib.
lang::uinteger uinteger
Type alias in namespace alib.
float maxLoadFactor
The maximum quotient of size and bucketCount that triggers a rehash.
lang::SidiNodeBase< Element > Node
Type of a node in the List.
typename HTElementSelector< TValueDescriptor, THashCaching >::Type Element
The type stored in the bucket of class HashTable.
typename RecyclingSelector< TRecycling >::template Type< TAllocator, typename HTElementSelector< TValueDescriptor, THashCaching >::Type > base
Our base type.
float baseLoadFactor
The load factor that is set when the table is rehashed automatically.
TElement * removeNext() noexcept