]>
git.proxmox.com Git - ceph.git/blob - ceph/src/include/compact_map.h
12ba8b3504a30e21b8e7f71b9dc50a2105352373
2 * Ceph - scalable distributed file system
4 * Copyright (C) 2015 Red Hat, Inc
6 * This is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License version 2.1, as published by the Free Software
9 * Foundation. See file COPYING.
12 #ifndef CEPH_COMPACT_MAP_H
13 #define CEPH_COMPACT_MAP_H
17 template <class Key
, class T
, class Map
>
18 class compact_map_base
{
21 void alloc_internal() {
25 void free_internal() {
32 class const_iterator_base
{
33 const compact_map_base
*map
;
35 const_iterator_base() : map(0) { }
36 const_iterator_base(const compact_map_base
* m
) : map(m
) { }
37 const_iterator_base(const compact_map_base
*m
, const It
& i
) : map(m
), it(i
) { }
38 friend class compact_map_base
;
39 friend class iterator_base
;
41 const_iterator_base(const const_iterator_base
& o
) {
45 bool operator==(const const_iterator_base
& o
) const {
46 return (map
== o
.map
) && (!map
->map
|| it
== o
.it
);
48 bool operator!=(const const_iterator_base
& o
) const {
49 return !(*this == o
);;
51 const_iterator_base
& operator=(const const_iterator_base
& o
) {
56 const_iterator_base
& operator++() {
60 const_iterator_base
& operator--() {
64 const std::pair
<const Key
,T
>* operator->() {
65 return it
.operator->();
71 const compact_map_base
* map
;
73 iterator_base() : map(0) { }
74 iterator_base(compact_map_base
* m
) : map(m
) { }
75 iterator_base(compact_map_base
* m
, const It
& i
) : map(m
), it(i
) { }
76 friend class compact_map_base
;
78 iterator_base(const iterator_base
& o
) {
82 bool operator==(const iterator_base
& o
) const {
83 return (map
== o
.map
) && (!map
->map
|| it
== o
.it
);
85 bool operator!=(const iterator_base
& o
) const {
86 return !(*this == o
);;
88 iterator_base
& operator=(const iterator_base
& o
) {
93 iterator_base
& operator++() {
97 iterator_base
operator++(int) {
98 iterator_base tmp
= *this;
102 iterator_base
& operator--() {
106 std::pair
<const Key
,T
>* operator->() {
107 return it
.operator->();
109 operator const_iterator_base
<It
>() const {
110 return const_iterator_base
<It
>(map
, it
);
115 class iterator
: public iterator_base
<typename
Map::iterator
> {
118 iterator(const iterator_base
<typename
Map::iterator
>& o
)
119 : iterator_base
<typename
Map::iterator
>(o
) { }
120 iterator(compact_map_base
* m
) : iterator_base
<typename
Map::iterator
>(m
) { }
121 iterator(compact_map_base
* m
, const typename
Map::iterator
& i
)
122 : iterator_base
<typename
Map::iterator
>(m
, i
) { }
124 class const_iterator
: public const_iterator_base
<typename
Map::const_iterator
> {
127 const_iterator(const iterator_base
<typename
Map::const_iterator
>& o
)
128 : const_iterator_base
<typename
Map::const_iterator
>(o
) { }
129 const_iterator(const compact_map_base
* m
) : const_iterator_base
<typename
Map::const_iterator
>(m
) { }
130 const_iterator(const compact_map_base
* m
, const typename
Map::const_iterator
& i
)
131 : const_iterator_base
<typename
Map::const_iterator
>(m
, i
) { }
133 class reverse_iterator
: public iterator_base
<typename
Map::reverse_iterator
> {
135 reverse_iterator() { }
136 reverse_iterator(const iterator_base
<typename
Map::reverse_iterator
>& o
)
137 : iterator_base
<typename
Map::reverse_iterator
>(o
) { }
138 reverse_iterator(compact_map_base
* m
) : iterator_base
<typename
Map::reverse_iterator
>(m
) { }
139 reverse_iterator(compact_map_base
* m
, const typename
Map::reverse_iterator
& i
)
140 : iterator_base
<typename
Map::reverse_iterator
>(m
, i
) { }
142 class const_reverse_iterator
: public const_iterator_base
<typename
Map::const_reverse_iterator
> {
144 const_reverse_iterator() { }
145 const_reverse_iterator(const iterator_base
<typename
Map::const_reverse_iterator
>& o
)
146 : iterator_base
<typename
Map::const_reverse_iterator
>(o
) { }
147 const_reverse_iterator(const compact_map_base
* m
) : const_iterator_base
<typename
Map::const_reverse_iterator
>(m
) { }
148 const_reverse_iterator(const compact_map_base
* m
, const typename
Map::const_reverse_iterator
& i
)
149 : const_iterator_base
<typename
Map::const_reverse_iterator
>(m
, i
) { }
151 compact_map_base() : map(0) {}
152 compact_map_base(const compact_map_base
& o
) : map(0) {
158 ~compact_map_base() { delete map
; }
161 return !map
|| map
->empty();
163 size_t size() const {
164 return map
? map
->size() : 0;
166 bool operator==(const compact_map_base
& o
) const {
167 return (empty() && o
.empty()) || (map
&& o
.map
&& *map
== *o
.map
);
169 bool operator!=(const compact_map_base
& o
) const {
170 return !(*this == o
);
172 size_t count (const Key
& k
) const {
173 return map
? map
->count(k
) : 0;
175 void erase (iterator p
) {
177 assert(this == p
.map
);
183 size_t erase (const Key
& k
) {
186 size_t r
= map
->erase(k
);
194 void swap(compact_map_base
& o
) {
199 compact_map_base
& operator=(const compact_map_base
& o
) {
207 iterator
insert(const std::pair
<const Key
, T
>& val
) {
209 return iterator(this, map
->insert(val
));
213 return iterator(this);
214 return iterator(this, map
->begin());
218 return iterator(this);
219 return iterator(this, map
->end());
221 reverse_iterator
rbegin() {
223 return reverse_iterator(this);
224 return reverse_iterator(this, map
->rbegin());
226 reverse_iterator
rend() {
228 return reverse_iterator(this);
229 return reverse_iterator(this, map
->rend());
231 iterator
find(const Key
& k
) {
233 return iterator(this);
234 return iterator(this, map
->find(k
));
236 iterator
lower_bound(const Key
& k
) {
238 return iterator(this);
239 return iterator(this, map
->lower_bound(k
));
241 iterator
upper_bound(const Key
& k
) {
243 return iterator(this);
244 return iterator(this, map
->upper_bound(k
));
246 const_iterator
begin() const {
248 return const_iterator(this);
249 return const_iterator(this, map
->begin());
251 const_iterator
end() const {
253 return const_iterator(this);
254 return const_iterator(this, map
->end());
256 const_reverse_iterator
rbegin() const {
258 return const_reverse_iterator(this);
259 return const_reverse_iterator(this, map
->rbegin());
261 const_reverse_iterator
rend() const {
263 return const_reverse_iterator(this);
264 return const_reverse_iterator(this, map
->rend());
266 const_iterator
find(const Key
& k
) const {
268 return const_iterator(this);
269 return const_iterator(this, map
->find(k
));
271 const_iterator
lower_bound(const Key
& k
) const {
273 return const_iterator(this);
274 return const_iterator(this, map
->lower_bound(k
));
276 const_iterator
upper_bound(const Key
& k
) const {
278 return const_iterator(this);
279 return const_iterator(this, map
->upper_bound(k
));
281 void encode(bufferlist
&bl
) const {
285 ::encode((uint32_t)0, bl
);
287 void encode(bufferlist
&bl
, uint64_t features
) const {
289 ::encode(*map
, bl
, features
);
291 ::encode((uint32_t)0, bl
);
293 void decode(bufferlist::iterator
& p
) {
298 ::decode_nohead(n
, *map
, p
);
304 template<class Key
, class T
, class Map
>
305 inline void encode(const compact_map_base
<Key
, T
, Map
>& m
, bufferlist
& bl
) {
308 template<class Key
, class T
, class Map
>
309 inline void encode(const compact_map_base
<Key
, T
, Map
>& m
, bufferlist
& bl
,
311 m
.encode(bl
, features
);
313 template<class Key
, class T
, class Map
>
314 inline void decode(compact_map_base
<Key
, T
, Map
>& m
, bufferlist::iterator
& p
) {
318 template <class Key
, class T
>
319 class compact_map
: public compact_map_base
<Key
, T
, std::map
<Key
,T
> > {
321 T
& operator[](const Key
& k
) {
322 this->alloc_internal();
323 return (*(this->map
))[k
];
327 template <class Key
, class T
>
328 inline std::ostream
& operator<<(std::ostream
& out
, const compact_map
<Key
, T
>& m
)
331 for (typename compact_map
<Key
, T
>::const_iterator it
= m
.begin();
336 out
<< it
->first
<< "=" << it
->second
;
342 template <class Key
, class T
>
343 class compact_multimap
: public compact_map_base
<Key
, T
, std::multimap
<Key
,T
> > {
346 template <class Key
, class T
>
347 inline std::ostream
& operator<<(std::ostream
& out
, const compact_multimap
<Key
, T
>& m
)
350 for (typename compact_map
<Key
, T
>::const_iterator it
= m
.begin(); !it
.end(); ++it
) {
353 out
<< it
->first
<< "=" << it
->second
;