• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

PeterCDMcLean / BitLib / 14919535413

09 May 2025 01:36AM UTC coverage: 96.956% (-0.08%) from 97.036%
14919535413

Pull #8

github

web-flow
Merge 708ead0cd into a837637fd
Pull Request #8: Common bit array base

36 of 38 new or added lines in 2 files covered. (94.74%)

4 existing lines in 3 files now uncovered.

1274 of 1314 relevant lines covered (96.96%)

16656585.79 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

96.3
/include/bitlib/bit-containers/bit_array_base.hpp
1
// ================================= BIT_ARRAY_BASE =================================== //
2
// Project:     The Experimental Bit Algorithms Library
3
// \file        bit_array_base.hpp
4
// Description: Base implementation for bit_array variants
5
// Creator:     Vincent Reverdy
6
// Contributor: Peter McLean [2025]
7
// License:     BSD 3-Clause License
8
// ========================================================================== //
9
#ifndef _BIT_ARRAY_BASE_HPP_INCLUDED
10
#define _BIT_ARRAY_BASE_HPP_INCLUDED
11
// ========================================================================== //
12

13
// ================================ PREAMBLE ================================ //
14
// C++ standard library
15
#include <algorithm>
16
#include <bit>
17
#include <cmath>
18
#include <span>
19
#include <string>
20
#include <type_traits>
21
#include <vector>
22
#include <cstring> // memcpy
23

24
// Project sources
25
#include "bitlib/bit-algorithms/bit_algorithm.hpp"
26
#include "bitlib/bit-containers/bit_bitsof.hpp"
27
#include "bitlib/bit-containers/bit_span.hpp"
28
#include "bitlib/bit-iterator/bit.hpp"
29

30
namespace bit {
31
// ========================================================================== //
32

33
/**
34
 * @brief Common utility functions for bit array implementations
35
 * @deprecated These functions have been moved to the bit_array_base class and will be removed in a future release
36
 */
37
namespace bit_array_utils {
38

39
    /**
40
     * @brief Generate a string representation of a range of bits
41
     *
42
     * @tparam Iterator The iterator type
43
     * @param first Iterator to the first bit
44
     * @param last Iterator past the last bit
45
     * @param digits The number of bits in a word
46
     * @return A string representation of the bits
47
     */
48
    template <typename Iterator>
49
    [[deprecated("Use bit_array_base::debug_string instead")]]
50
    constexpr std::string debug_string_impl(Iterator first, Iterator last, std::size_t digits) {
51
        std::string ret = "";
52
        auto position = 0;
53
        for (auto it = first; it != last; ++it) {
54
            if (position % digits == 0 && position != 0) {
55
                ret += " ";
56
            } else if (position % 8 == 0 && position != 0) {
57
                ret += '.';
58
            }
59
            ret += *it == bit1 ? '1' : '0';
60
            ++position;
61
        }
62
        return ret;
63
    }
64

65
    /**
66
     * @brief Element access helper for at() method
67
     */
68
    template <typename Container>
69
    [[deprecated("Use bit_array_base::at instead")]]
70
    constexpr auto at_impl(Container& container, typename Container::size_type pos)
71
        -> decltype(container.begin()[pos]) {
72
        if (pos < container.size()) {
73
            return container.begin()[pos];
74
        } else {
75
            throw std::out_of_range("Position is out of range");
76
        }
77
    }
78

79
    /**
80
     * @brief Equality comparison implementation
81
     */
82
    template <typename Container>
83
    [[deprecated("Use bit_array_base::operator== instead")]]
84
    constexpr bool equal_impl(const Container& lhs, const Container& rhs) {
85
        return equal(lhs.begin(), lhs.end(), rhs.begin());
86
    }
87

88
} // namespace bit_array_utils
89

90
/**
91
 * @brief Base class template for bit_array implementations
92
 *
93
 * This is a CRTP (Curiously Recurring Template Pattern) base class that provides
94
 * common functionality for bit_array variants.
95
 *
96
 * @tparam Derived The derived class (CRTP pattern)
97
 * @tparam T The value type (typically bit_value)
98
 * @tparam W The word type used for storage
99
 * @tparam It The iterator type for the derived class
100
 * @tparam CIt The const_iterator type for the derived class
101
 */
102
template <typename Derived, typename T, typename W, typename It, typename CIt>
103
class bit_array_base {
104
public:
105
    using word_type = W;
106
    using value_type = T;
107
    using size_type = std::size_t;
108
    using difference_type = std::ptrdiff_t;
109
    using reference = typename std::conditional<std::is_same_v<T, bit_value>, bit_reference<word_type>, T&>::type;
110
    using const_reference = typename std::conditional<std::is_same_v<T, bit_value>, const bit_reference<const word_type>, const T&>::type;
111
    using pointer = typename std::conditional<std::is_same_v<T, bit_value>, bit_pointer<word_type>, T&>::type;
112
    using const_pointer = const pointer;
113
    using iterator = It;
114
    using const_iterator = CIt;
115

116
    // Element access
117
    constexpr reference operator[](size_type pos) {
593✔
118
        return derived().begin()[pos];
1,184✔
119
    }
120

121
    constexpr const_reference operator[](size_type pos) const {
122
        return derived().begin()[pos];
123
    }
124

125
    constexpr reference at(size_type pos) {
5✔
126
        if (pos < derived().size()) {
5✔
127
            return derived().begin()[pos];
8✔
128
        } else {
129
            throw std::out_of_range("Position is out of range");
1✔
130
        }
131
    }
132

133
    constexpr const_reference at(size_type pos) const {
134
        if (pos < derived().size()) {
135
            return derived().begin()[pos];
136
        } else {
137
            throw std::out_of_range("Position is out of range");
138
        }
139
    }
140

141
    constexpr reference front() {
3✔
142
        return derived().begin()[0];
6✔
143
    }
144

145
    constexpr const_reference front() const {
146
        return derived().begin()[0];
147
    }
148

149
    constexpr reference back() {
3✔
150
        return derived().begin()[derived().size() - 1];
6✔
151
    }
152

153
    constexpr const_reference back() const {
154
        return derived().begin()[derived().size() - 1];
155
    }
156

157
    // Capacity
158
    constexpr bool empty() const noexcept {
4✔
159
        return 0 == derived().size();
4✔
160
    }
161

162
    constexpr size_type max_size() const noexcept {
1✔
163
        return derived().size();
1✔
164
    }
165

166
    // String representation
167
    constexpr std::string debug_string() const {
168
        return debug_string(derived().begin(), derived().end());
169
    }
170

171
    constexpr std::string debug_string(const_iterator first, const_iterator last) const {
172
        std::string ret = "";
173
        auto position = 0;
174
        for (auto it = first; it != last; ++it) {
175
            if (position % bitsof<word_type>() == 0 && position != 0) {
176
                ret += " ";
177
            } else if (position % 8 == 0 && position != 0) {
178
                ret += '.';
179
            }
180
            ret += *it == bit1 ? '1' : '0';
181
            ++position;
182
        }
183
        return ret;
184
    }
185

186
    // Comparison
187
    constexpr bool operator==(const Derived& other) const noexcept {
8✔
188
        if (derived().size() != other.size()) {
8✔
NEW
189
            return false;
×
190
        }
191
        return equal(derived().begin(), derived().end(), other.begin());
8✔
192
    }
193

194
    // Slice operations
195
    constexpr auto operator()(size_type offset, size_type right) const noexcept {
196
        return bit_span<const word_type, std::dynamic_extent>(&this->at(offset), right - offset);
197
    }
198

199
    constexpr auto operator()(size_type offset, size_type right) noexcept {
2✔
200
        return bit_span<word_type, std::dynamic_extent>(&this->at(offset), right - offset);
2✔
201
    }
202

203
    // Common operations
204
    constexpr void fill(value_type bit_val) noexcept {
22✔
205
        std::fill(derived().begin(), derived().end(), bit_val);
22✔
206
    }
22✔
207

208
protected:
209
    constexpr Derived& derived() noexcept {
655✔
210
        return static_cast<Derived&>(*this);
655✔
211
    }
212

213
    constexpr const Derived& derived() const noexcept {
29✔
214
        return static_cast<const Derived&>(*this);
29✔
215
    }
216
};
217

218
} // namespace bit
219

220
#endif // _BIT_ARRAY_BASE_HPP_INCLUDED
221
// ========================================================================== //
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc