From: Rafael Espindola Date: Wed, 19 Sep 2012 13:42:51 +0000 (+0000) Subject: Make MapVector a bit more expensive but harder to misuse. We now only X-Git-Url: http://plrg.eecs.uci.edu/git/?a=commitdiff_plain;h=c312f098999d4640cf91934632ccecfc9ef30b85;p=oota-llvm.git Make MapVector a bit more expensive but harder to misuse. We now only provide insertion order iteration, instead of the old option of DenseMap order iteration over keys and insertion order iteration over values. This is implemented by keeping two copies of each key. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@164221 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/llvm/ADT/MapVector.h b/include/llvm/ADT/MapVector.h index be3845f1d27..bad207baa90 100644 --- a/include/llvm/ADT/MapVector.h +++ b/include/llvm/ADT/MapVector.h @@ -7,10 +7,10 @@ // //===----------------------------------------------------------------------===// // -// This file implements a map that also provides access to all stored values -// in a deterministic order via the getValues method. Note that the iteration -// order itself is just the DenseMap order and not deterministic. The interface -// is purposefully minimal. +// This file implements a map that provides insertion order iteration. The +// interface is purposefully minimal. The key is assumed to be cheap to copy +// and 2 copies are kept, one for indexing in a DenseMap, one for iteration in +// a std::vector. // //===----------------------------------------------------------------------===// @@ -29,111 +29,38 @@ namespace llvm { template class MapVector { typedef llvm::DenseMap MapType; - typedef std::vector VectorType; + typedef std::vector > VectorType; typedef typename VectorType::size_type SizeType; MapType Map; VectorType Vector; public: - // The keys and values are not stored close to each other, so the iterator - // operator->() cannot return a pointer to a std::pair like a DenseMap does. - // Instead it returns a FakePair that contains references to Key and Value. - // This lets code using this to look the same as if using a regular DenseMap. - template - struct FakePair { - typedef typename conditional::type VT; - const KeyT &first; - VT &second; - FakePair(const KeyT &K, VT &V) : first(K), second(V) { - } - FakePair *operator->() { - return this; - } - }; - - template - class IteratorTemplate { - typedef typename MapType::const_iterator WrappedIteratorType; - WrappedIteratorType WrappedI; - typedef - typename conditional::type VT; - VT &VecRef; - typedef FakePair PairType; - friend class IteratorTemplate; - - public: - IteratorTemplate(WrappedIteratorType I, VT &V) : - WrappedI(I), VecRef(V) { - } - - // If IsConst is true this is a converting constructor from iterator to - // const_iterator and the default copy constructor is used. - // Otherwise this is a copy constructor for iterator. - IteratorTemplate(const IteratorTemplate& I) : - WrappedI(I.WrappedI), VecRef(I.VecRef) { - } - - bool operator!=(const IteratorTemplate &RHS) const { - return WrappedI != RHS.WrappedI; - } - - IteratorTemplate &operator++() { // Preincrement - ++WrappedI; - return *this; - } - - PairType operator->() { - unsigned Pos = WrappedI->second; - PairType Ret(WrappedI->first, VecRef[Pos]); - return Ret; - } - }; - - typedef IteratorTemplate iterator; - typedef IteratorTemplate const_iterator; + typedef typename VectorType::iterator iterator; + typedef typename VectorType::const_iterator const_iterator; SizeType size() const { return Vector.size(); } iterator begin() { - return iterator(Map.begin(), this->Vector); + return Vector.begin(); } const_iterator begin() const { - return const_iterator(Map.begin(), this->Vector); + return Vector.begin(); } iterator end() { - return iterator(Map.end(), this->Vector); + return Vector.end(); } const_iterator end() const { - return const_iterator(Map.end(), this->Vector); - } - - bool empty() const { - return Map.empty(); - } - - typedef typename VectorType::iterator value_iterator; - typedef typename VectorType::const_iterator const_value_iterator; - - value_iterator value_begin() { - return Vector.begin(); - } - - const_value_iterator value_begin() const { - return Vector.begin(); - } - - value_iterator value_end() { return Vector.end(); } - const_value_iterator value_end() const { - return Vector.end(); + bool empty() const { + return Vector.empty(); } ValueT &operator[](const KeyT &Key) { @@ -141,10 +68,10 @@ public: std::pair Result = Map.insert(Pair); unsigned &I = Result.first->second; if (Result.second) { - Vector.push_back(ValueT()); + Vector.push_back(std::make_pair(Key, ValueT())); I = Vector.size() - 1; } - return Vector[I]; + return Vector[I].second; } };