Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/Common/ScopedMap.h

    rccb29b4 rdf00c78  
    3737                template<typename N>
    3838                Scope(N && n) : map(), note(std::forward<N>(n)) {}
    39 
     39               
    4040                Scope() = default;
    4141                Scope(const Scope &) = default;
     
    4646        typedef std::vector< Scope > ScopeList;
    4747
    48         /// Scoped list of maps.
    49         ScopeList scopes;
     48        ScopeList scopes; ///< scoped list of maps
    5049public:
    5150        typedef typename MapType::key_type key_type;
     
    5958        typedef typename MapType::const_pointer const_pointer;
    6059
    61         // Both iterator types are complete bidrectional iterators, see below.
    62         class iterator;
    63         class const_iterator;
     60        class iterator : public std::iterator< std::bidirectional_iterator_tag, value_type > {
     61        friend class ScopedMap;
     62        friend class const_iterator;
     63                typedef typename ScopedMap::MapType::iterator wrapped_iterator;
     64                typedef typename ScopedMap::ScopeList scope_list;
     65                typedef typename scope_list::size_type size_type;
     66
     67                /// Checks if this iterator points to a valid item
     68                bool is_valid() const {
     69                        return it != (*scopes)[level].map.end();
     70                }
     71
     72                /// Increments on invalid
     73                iterator & next_valid() {
     74                        if ( ! is_valid() ) { ++(*this); }
     75                        return *this;
     76                }
     77
     78                /// Decrements on invalid
     79                iterator & prev_valid() {
     80                        if ( ! is_valid() ) { --(*this); }
     81                        return *this;
     82                }
     83
     84                iterator(scope_list & _scopes, const wrapped_iterator & _it, size_type inLevel)
     85                        : scopes(&_scopes), it(_it), level(inLevel) {}
     86        public:
     87                iterator(const iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
     88                iterator & operator= (const iterator & that) {
     89                        scopes = that.scopes; level = that.level; it = that.it;
     90                        return *this;
     91                }
     92
     93                reference operator* () { return *it; }
     94                pointer operator-> () const { return it.operator->(); }
     95
     96                iterator & operator++ () {
     97                        if ( it == (*scopes)[level].map.end() ) {
     98                                if ( level == 0 ) return *this;
     99                                --level;
     100                                it = (*scopes)[level].map.begin();
     101                        } else {
     102                                ++it;
     103                        }
     104                        return next_valid();
     105                }
     106                iterator operator++ (int) { iterator tmp = *this; ++(*this); return tmp; }
     107
     108                iterator & operator-- () {
     109                        // may fail if this is the begin iterator; allowed by STL spec
     110                        if ( it == (*scopes)[level].map.begin() ) {
     111                                ++level;
     112                                it = (*scopes)[level].map.end();
     113                        }
     114                        --it;
     115                        return prev_valid();
     116                }
     117                iterator operator-- (int) { iterator tmp = *this; --(*this); return tmp; }
     118
     119                bool operator== (const iterator & that) const {
     120                        return scopes == that.scopes && level == that.level && it == that.it;
     121                }
     122                bool operator!= (const iterator & that) const { return !( *this == that ); }
     123
     124                size_type get_level() const { return level; }
     125
     126                Note & get_note() { return (*scopes)[level].note; }
     127                const Note & get_note() const { return (*scopes)[level].note; }
     128
     129        private:
     130                scope_list *scopes;
     131                wrapped_iterator it;
     132                size_type level;
     133        };
     134
     135        class const_iterator : public std::iterator< std::bidirectional_iterator_tag,
     136                                                     value_type > {
     137        friend class ScopedMap;
     138                typedef typename ScopedMap::MapType::iterator wrapped_iterator;
     139                typedef typename ScopedMap::MapType::const_iterator wrapped_const_iterator;
     140                typedef typename ScopedMap::ScopeList scope_list;
     141                typedef typename scope_list::size_type size_type;
     142
     143                /// Checks if this iterator points to a valid item
     144                bool is_valid() const {
     145                        return it != (*scopes)[level].map.end();
     146                }
     147
     148                /// Increments on invalid
     149                const_iterator & next_valid() {
     150                        if ( ! is_valid() ) { ++(*this); }
     151                        return *this;
     152                }
     153
     154                /// Decrements on invalid
     155                const_iterator & prev_valid() {
     156                        if ( ! is_valid() ) { --(*this); }
     157                        return *this;
     158                }
     159
     160                const_iterator(scope_list const & _scopes, const wrapped_const_iterator & _it, size_type inLevel)
     161                        : scopes(&_scopes), it(_it), level(inLevel) {}
     162        public:
     163                const_iterator(const iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
     164                const_iterator(const const_iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
     165                const_iterator & operator= (const iterator & that) {
     166                        scopes = that.scopes; level = that.level; it = that.it;
     167                        return *this;
     168                }
     169                const_iterator & operator= (const const_iterator & that) {
     170                        scopes = that.scopes; level = that.level; it = that.it;
     171                        return *this;
     172                }
     173
     174                const_reference operator* () { return *it; }
     175                const_pointer operator-> () { return it.operator->(); }
     176
     177                const_iterator & operator++ () {
     178                        if ( it == (*scopes)[level].map.end() ) {
     179                                if ( level == 0 ) return *this;
     180                                --level;
     181                                it = (*scopes)[level].map.begin();
     182                        } else {
     183                                ++it;
     184                        }
     185                        return next_valid();
     186                }
     187                const_iterator operator++ (int) { const_iterator tmp = *this; ++(*this); return tmp; }
     188
     189                const_iterator & operator-- () {
     190                        // may fail if this is the begin iterator; allowed by STL spec
     191                        if ( it == (*scopes)[level].map.begin() ) {
     192                                ++level;
     193                                it = (*scopes)[level].map.end();
     194                        }
     195                        --it;
     196                        return prev_valid();
     197                }
     198                const_iterator operator-- (int) { const_iterator tmp = *this; --(*this); return tmp; }
     199
     200                bool operator== (const const_iterator & that) const {
     201                        return scopes == that.scopes && level == that.level && it == that.it;
     202                }
     203                bool operator!= (const const_iterator & that) const { return !( *this == that ); }
     204
     205                size_type get_level() const { return level; }
     206
     207                const Note & get_note() const { return (*scopes)[level].note; }
     208
     209        private:
     210                scope_list const *scopes;
     211                wrapped_const_iterator it;
     212                size_type level;
     213        };
    64214
    65215        /// Starts a new scope
     
    147297        }
    148298
     299        template< typename value_type_t >
     300        std::pair< iterator, bool > insert( iterator at, value_type_t && value ) {
     301                MapType & scope = (*at.scopes)[ at.level ].map;
     302                std::pair< typename MapType::iterator, bool > res = scope.insert( std::forward<value_type_t>( value ) );
     303                return std::make_pair( iterator(scopes, std::move( res.first ), at.level), std::move( res.second ) );
     304        }
     305
    149306        template< typename value_t >
    150307        std::pair< iterator, bool > insert( const Key & key, value_t && value ) { return insert( std::make_pair( key, std::forward<value_t>( value ) ) ); }
     
    167324        }
    168325
    169         /// Erases element with key in the innermost scope that has it.
    170         size_type erase( const Key & key ) {
    171                 for ( auto it = scopes.rbegin() ; it != scopes.rend() ; ++it ) {
    172                         size_type i = it->map.erase( key );
    173                         if ( 0 != i ) return i;
    174                 }
    175                 return 0;
     326        iterator erase( iterator pos ) {
     327                MapType & scope = (*pos.scopes)[ pos.level ].map;
     328                const typename iterator::wrapped_iterator & new_it = scope.erase( pos.it );
     329                iterator it( *pos.scopes, new_it, pos.level );
     330                return it.next_valid();
    176331        }
    177332
     
    188343                return c;
    189344        }
    190 
    191         bool contains( const Key & key ) const {
    192                 return find( key ) != cend();
    193         }
    194 };
    195 
    196 template<typename Key, typename Value, typename Note>
    197 class ScopedMap<Key, Value, Note>::iterator :
    198                 public std::iterator< std::bidirectional_iterator_tag, value_type > {
    199         friend class ScopedMap;
    200         friend class const_iterator;
    201         typedef typename ScopedMap::MapType::iterator wrapped_iterator;
    202         typedef typename ScopedMap::ScopeList scope_list;
    203         typedef typename scope_list::size_type size_type;
    204 
    205         /// Checks if this iterator points to a valid item
    206         bool is_valid() const {
    207                 return it != (*scopes)[level].map.end();
    208         }
    209 
    210         /// Increments on invalid
    211         iterator & next_valid() {
    212                 if ( ! is_valid() ) { ++(*this); }
    213                 return *this;
    214         }
    215 
    216         /// Decrements on invalid
    217         iterator & prev_valid() {
    218                 if ( ! is_valid() ) { --(*this); }
    219                 return *this;
    220         }
    221 
    222         iterator(scope_list & _scopes, const wrapped_iterator & _it, size_type inLevel)
    223                 : scopes(&_scopes), it(_it), level(inLevel) {}
    224 public:
    225         iterator(const iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
    226         iterator & operator= (const iterator & that) {
    227                 scopes = that.scopes; level = that.level; it = that.it;
    228                 return *this;
    229         }
    230 
    231         reference operator* () { return *it; }
    232         pointer operator-> () const { return it.operator->(); }
    233 
    234         iterator & operator++ () {
    235                 if ( it == (*scopes)[level].map.end() ) {
    236                         if ( level == 0 ) return *this;
    237                         --level;
    238                         it = (*scopes)[level].map.begin();
    239                 } else {
    240                         ++it;
    241                 }
    242                 return next_valid();
    243         }
    244         iterator operator++ (int) { iterator tmp = *this; ++(*this); return tmp; }
    245 
    246         iterator & operator-- () {
    247                 // may fail if this is the begin iterator; allowed by STL spec
    248                 if ( it == (*scopes)[level].map.begin() ) {
    249                         ++level;
    250                         it = (*scopes)[level].map.end();
    251                 }
    252                 --it;
    253                 return prev_valid();
    254         }
    255         iterator operator-- (int) { iterator tmp = *this; --(*this); return tmp; }
    256 
    257         bool operator== (const iterator & that) const {
    258                 return scopes == that.scopes && level == that.level && it == that.it;
    259         }
    260         bool operator!= (const iterator & that) const { return !( *this == that ); }
    261 
    262         size_type get_level() const { return level; }
    263 
    264         Note & get_note() { return (*scopes)[level].note; }
    265         const Note & get_note() const { return (*scopes)[level].note; }
    266 
    267 private:
    268         scope_list *scopes;
    269         wrapped_iterator it;
    270         size_type level;
    271 };
    272 
    273 template<typename Key, typename Value, typename Note>
    274 class ScopedMap<Key, Value, Note>::const_iterator :
    275                 public std::iterator< std::bidirectional_iterator_tag, value_type > {
    276         friend class ScopedMap;
    277         typedef typename ScopedMap::MapType::iterator wrapped_iterator;
    278         typedef typename ScopedMap::MapType::const_iterator wrapped_const_iterator;
    279         typedef typename ScopedMap::ScopeList scope_list;
    280         typedef typename scope_list::size_type size_type;
    281 
    282         /// Checks if this iterator points to a valid item
    283         bool is_valid() const {
    284                 return it != (*scopes)[level].map.end();
    285         }
    286 
    287         /// Increments on invalid
    288         const_iterator & next_valid() {
    289                 if ( ! is_valid() ) { ++(*this); }
    290                 return *this;
    291         }
    292 
    293         /// Decrements on invalid
    294         const_iterator & prev_valid() {
    295                 if ( ! is_valid() ) { --(*this); }
    296                 return *this;
    297         }
    298 
    299         const_iterator(scope_list const & _scopes, const wrapped_const_iterator & _it, size_type inLevel)
    300                 : scopes(&_scopes), it(_it), level(inLevel) {}
    301 public:
    302         const_iterator(const iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
    303         const_iterator(const const_iterator & that) : scopes(that.scopes), it(that.it), level(that.level) {}
    304         const_iterator & operator= (const iterator & that) {
    305                 scopes = that.scopes; level = that.level; it = that.it;
    306                 return *this;
    307         }
    308         const_iterator & operator= (const const_iterator & that) {
    309                 scopes = that.scopes; level = that.level; it = that.it;
    310                 return *this;
    311         }
    312 
    313         const_reference operator* () { return *it; }
    314         const_pointer operator-> () { return it.operator->(); }
    315 
    316         const_iterator & operator++ () {
    317                 if ( it == (*scopes)[level].map.end() ) {
    318                         if ( level == 0 ) return *this;
    319                         --level;
    320                         it = (*scopes)[level].map.begin();
    321                 } else {
    322                         ++it;
    323                 }
    324                 return next_valid();
    325         }
    326         const_iterator operator++ (int) { const_iterator tmp = *this; ++(*this); return tmp; }
    327 
    328         const_iterator & operator-- () {
    329                 // may fail if this is the begin iterator; allowed by STL spec
    330                 if ( it == (*scopes)[level].map.begin() ) {
    331                         ++level;
    332                         it = (*scopes)[level].map.end();
    333                 }
    334                 --it;
    335                 return prev_valid();
    336         }
    337         const_iterator operator-- (int) { const_iterator tmp = *this; --(*this); return tmp; }
    338 
    339         bool operator== (const const_iterator & that) const {
    340                 return scopes == that.scopes && level == that.level && it == that.it;
    341         }
    342         bool operator!= (const const_iterator & that) const { return !( *this == that ); }
    343 
    344         size_type get_level() const { return level; }
    345 
    346         const Note & get_note() const { return (*scopes)[level].note; }
    347 
    348 private:
    349         scope_list const *scopes;
    350         wrapped_const_iterator it;
    351         size_type level;
    352345};
    353346
Note: See TracChangeset for help on using the changeset viewer.