Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #ifndef INCLUDED_O3TL_ENUMARRAY_HXX
21 : #define INCLUDED_O3TL_ENUMARRAY_HXX
22 :
23 : #include <sal/config.h>
24 : #include <iterator>
25 :
26 : namespace o3tl {
27 :
28 : template<typename EA>
29 : class enumarray_iterator;
30 :
31 : ///
32 : /// This is a container convenience class for arrays indexed by enum values.
33 : ///
34 : /// This assumes that the 'enum class' definition
35 : /// - starts at zero
36 : /// - has no holes in it's sequence of values
37 : /// - defines a value called LAST which refers to the greatest constant.
38 : ///
39 : /// \param E the 'enum class' type.
40 : /// \param V the value type to be stored in the array
41 : template<typename E, typename V>
42 941 : class enumarray SAL_FINAL
43 : {
44 : public:
45 : typedef enumarray<E, V> self_type;
46 : typedef enumarray_iterator<self_type> iterator;
47 :
48 : typedef V value_type;
49 : typedef E key_type;
50 : typedef size_t size_type;
51 :
52 : static const size_type max_index = static_cast<size_type>(E::LAST);
53 :
54 9448042 : const V& operator[](E index) const
55 : {
56 : assert(index>=static_cast<E>(0) && index<=E::LAST);
57 9448042 : return detail_values[static_cast<size_type>(index)];
58 : }
59 :
60 1760004 : V& operator[](E index)
61 : {
62 : assert(index>=static_cast<E>(0) && index<=E::LAST);
63 1760004 : return detail_values[static_cast<size_type>(index)];
64 : }
65 :
66 11 : void fill(V val)
67 11 : { for (size_type i=0; i<=max_index; ++i) detail_values[i] = val; }
68 :
69 171043 : static size_type size() { return max_index + 1; }
70 85572 : iterator begin() { return iterator(*this, 0); }
71 171019 : iterator end() { return iterator(*this, size()); }
72 :
73 24 : V* data() { return detail_values; }
74 :
75 : //private:
76 : V detail_values[max_index + 1];
77 : };
78 :
79 :
80 : template<typename EA>
81 : class enumarray_iterator {
82 : EA *m_buf;
83 : size_t m_pos;
84 : public:
85 : typedef enumarray_iterator<EA> self_type;
86 : typedef typename EA::value_type value_type;
87 : typedef typename EA::key_type key_type;
88 : typedef std::bidirectional_iterator_tag iterator_category; //should be random access, but that would require define subtraction operators on the enums
89 : typedef typename EA::key_type difference_type;
90 : typedef typename EA::value_type* pointer;
91 : typedef typename EA::value_type& reference;
92 :
93 256591 : enumarray_iterator(EA& b, size_t start_pos)
94 256591 : : m_buf(&b), m_pos(start_pos) {}
95 1680949 : value_type &operator*() { return (*m_buf)[static_cast<key_type>(m_pos)]; }
96 : value_type *operator->() { return &(operator*()); }
97 1601389 : self_type &operator++() { ++m_pos; return *this; }
98 1732628 : bool operator!=(const self_type& other) { return m_buf != other.m_buf || m_pos != other.m_pos; }
99 39780 : bool operator==(const self_type& other) { return m_buf == other.m_buf && m_pos == other.m_pos; }
100 : };
101 :
102 : }; // namespace o3tl
103 :
104 : #endif /* INCLUDED_O3TL_ENUMARRAY_HXX */
105 :
106 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|