From 784de75ca8d449fef5493ad9c0a926b3b4b37b03 Mon Sep 17 00:00:00 2001 From: Chandler Carruth Date: Mon, 3 Feb 2014 11:24:21 +0000 Subject: [PATCH] Introduce SmallPtrSetImpl which allows insert, erase, count, and iteration. This alows the majority of operations to be performed without encoding a specific small size. It follows the model of SmallVectorImpl. llvm-svn: 200688 --- llvm/include/llvm/ADT/SmallPtrSet.h | 67 +++++++++++++++++++---------- 1 file changed, 45 insertions(+), 22 deletions(-) diff --git a/llvm/include/llvm/ADT/SmallPtrSet.h b/llvm/include/llvm/ADT/SmallPtrSet.h index b07300532148..03d8990cb487 100644 --- a/llvm/include/llvm/ADT/SmallPtrSet.h +++ b/llvm/include/llvm/ADT/SmallPtrSet.h @@ -235,30 +235,27 @@ struct RoundUpToPowerOfTwo { }; -/// SmallPtrSet - This class implements a set which is optimized for holding -/// SmallSize or less elements. This internally rounds up SmallSize to the next -/// power of two if it is not already a power of two. See the comments above -/// SmallPtrSetImplBase for details of the algorithm. -template -class SmallPtrSet : public SmallPtrSetImplBase { - // Make sure that SmallSize is a power of two, round up if not. - enum { SmallSizePowTwo = RoundUpToPowerOfTwo::Val }; - /// SmallStorage - Fixed size storage used in 'small mode'. - const void *SmallStorage[SmallSizePowTwo]; +/// \brief A templated base class for \c SmallPtrSet which provides the +/// typesafe interface that is common across all small sizes. +/// +/// This is particularly useful for passing around between interface boundaries +/// to avoid encoding a particular small size in the interface boundary. +template +class SmallPtrSetImpl : public SmallPtrSetImplBase { typedef PointerLikeTypeTraits PtrTraits; -public: - SmallPtrSet() : SmallPtrSetImplBase(SmallStorage, SmallSizePowTwo) {} - SmallPtrSet(const SmallPtrSet &that) : SmallPtrSetImplBase(SmallStorage, that) {} +protected: + // Constructors that forward to the base. + SmallPtrSetImpl(const void **SmallStorage, const SmallPtrSetImpl &that) + : SmallPtrSetImplBase(SmallStorage, that) {} #if LLVM_HAS_RVALUE_REFERENCES - SmallPtrSet(SmallPtrSet &&that) - : SmallPtrSetImplBase(SmallStorage, SmallSizePowTwo, std::move(that)) {} + SmallPtrSetImpl(const void **SmallStorage, unsigned SmallSize, + SmallPtrSetImpl &&that) + : SmallPtrSetImplBase(SmallStorage, SmallSize, std::move(that)) {} #endif + explicit SmallPtrSetImpl(const void **SmallStorage, unsigned SmallSize) + : SmallPtrSetImplBase(SmallStorage, SmallSize) {} - template - SmallPtrSet(It I, It E) : SmallPtrSetImplBase(SmallStorage, SmallSizePowTwo) { - insert(I, E); - } - +public: /// insert - This returns true if the pointer was new to the set, false if it /// was already in the set. bool insert(PtrType Ptr) { @@ -290,11 +287,37 @@ public: inline iterator end() const { return iterator(CurArray+CurArraySize, CurArray+CurArraySize); } +}; + +/// SmallPtrSet - This class implements a set which is optimized for holding +/// SmallSize or less elements. This internally rounds up SmallSize to the next +/// power of two if it is not already a power of two. See the comments above +/// SmallPtrSetImplBase for details of the algorithm. +template +class SmallPtrSet : public SmallPtrSetImpl { + typedef SmallPtrSetImpl BaseT; + + // Make sure that SmallSize is a power of two, round up if not. + enum { SmallSizePowTwo = RoundUpToPowerOfTwo::Val }; + /// SmallStorage - Fixed size storage used in 'small mode'. + const void *SmallStorage[SmallSizePowTwo]; +public: + SmallPtrSet() : BaseT(SmallStorage, SmallSizePowTwo) {} + SmallPtrSet(const SmallPtrSet &that) : BaseT(SmallStorage, that) {} +#if LLVM_HAS_RVALUE_REFERENCES + SmallPtrSet(SmallPtrSet &&that) + : BaseT(SmallStorage, SmallSizePowTwo, std::move(that)) {} +#endif + + template + SmallPtrSet(It I, It E) : BaseT(SmallStorage, SmallSizePowTwo) { + this->insert(I, E); + } SmallPtrSet & operator=(const SmallPtrSet &RHS) { if (&RHS != this) - CopyFrom(RHS); + this->CopyFrom(RHS); return *this; } @@ -302,7 +325,7 @@ public: SmallPtrSet& operator=(SmallPtrSet &&RHS) { if (&RHS != this) - MoveFrom(SmallSizePowTwo, std::move(RHS)); + this->MoveFrom(SmallSizePowTwo, std::move(RHS)); return *this; } #endif