sparrow 0.9.0
Loading...
Searching...
No Matches
array_base.hpp
Go to the documentation of this file.
1// Copyright 2024 Man Group Operations Limited
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or mplied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15#pragma once
16
17#include <algorithm>
18#include <cstddef>
19#include <cstdint>
20#include <ranges>
21#include <utility>
22
30
31namespace sparrow
32{
43
50 template <class D>
52
65 template <class D>
66 class array_crtp_base : public crtp_base<D>
67 {
68 public:
69
71 using derived_type = D;
72
74
75 using size_type = std::size_t;
76 using difference_type = std::ptrdiff_t;
77
78 using bitmap_type = typename inner_types::bitmap_type;
79 using bitmap_const_reference = bitmap_type::const_reference;
80 using bitmap_iterator = bitmap_type::iterator;
81 using const_bitmap_iterator = bitmap_type::const_iterator;
82 using const_bitmap_range = std::ranges::subrange<const_bitmap_iterator>;
83
84 using inner_value_type = typename inner_types::inner_value_type;
86
87 using inner_const_reference = typename inner_types::inner_const_reference;
89
90 using const_value_iterator = typename inner_types::const_value_iterator;
91 using const_value_range = std::ranges::subrange<const_value_iterator>;
92
93 using iterator_tag = typename inner_types::iterator_tag;
94
103
105 using const_reverse_iterator = std::reverse_iterator<const_iterator>;
106
107 [[nodiscard]] std::optional<std::string_view> name() const;
108 [[nodiscard]] std::optional<key_value_view> metadata() const;
109
110 [[nodiscard]] bool empty() const;
111 [[nodiscard]] size_type size() const;
112
113 [[nodiscard]] const_reference at(size_type i) const;
114 [[nodiscard]] const_reference operator[](size_type i) const;
115 [[nodiscard]] const_reference front() const;
116 [[nodiscard]] const_reference back() const;
117
118 [[nodiscard]] const_iterator begin() const;
119 [[nodiscard]] const_iterator end() const;
120
121 [[nodiscard]] const_iterator cbegin() const;
122 [[nodiscard]] const_iterator cend() const;
123
124 [[nodiscard]] const_reverse_iterator rbegin() const;
125 [[nodiscard]] const_reverse_iterator rend() const;
126
127 [[nodiscard]] const_reverse_iterator crbegin() const;
128 [[nodiscard]] const_reverse_iterator crend() const;
129
130 [[nodiscard]] const_bitmap_range bitmap() const;
131 [[nodiscard]] const_value_range values() const;
132
142 [[nodiscard]] D slice(size_type start, size_type end) const;
143
153 [[nodiscard]] D slice_view(size_type start, size_type end) const;
154
155 protected:
156
158
161
162 array_crtp_base(array_crtp_base&&) noexcept = default;
163 array_crtp_base& operator=(array_crtp_base&&) noexcept = default;
164
165 [[nodiscard]] arrow_proxy& get_arrow_proxy();
166 [[nodiscard]] const arrow_proxy& get_arrow_proxy() const;
167
169
172
175
176 private:
177
178 arrow_proxy m_proxy;
179
180 // friend classes
181 friend class layout_iterator<iterator_types>;
182 friend class detail::array_access;
183#if defined(__cpp_lib_format)
184 friend struct std::formatter<D>;
185#endif
186 };
187
188 template <class D>
189 bool operator==(const array_crtp_base<D>& lhs, const array_crtp_base<D>& rhs);
190
191 /**********************************
192 * array_crtp_base implementation *
193 **********************************/
194
195 template <class D>
196 std::optional<std::string_view> array_crtp_base<D>::name() const
197 {
198 return get_arrow_proxy().name();
199 }
200
201 template <class D>
202 std::optional<key_value_view> array_crtp_base<D>::metadata() const
203 {
204 return get_arrow_proxy().metadata();
205 }
206
210 template <class D>
212 {
213 return size() == size_type(0);
214 }
215
219 template <class D>
221 {
222 return static_cast<size_type>(get_arrow_proxy().length());
223 }
224
231 template <class D>
233 {
234 if (i >= size())
235 {
236 std::ostringstream oss117;
237 oss117 << "Index " << i << "is greater or equal to size of array (" << size() << ")";
238 throw std::out_of_range(oss117.str());
239 }
240 return (*this)[i];
241 }
242
248 template <class D>
250 {
251 auto& derived_cast = this->derived_cast();
253 return const_reference(inner_const_reference(derived_cast.value(i)), derived_cast.has_value(i));
254 }
255
260 template <class D>
262 {
264 return (*this)[size_type(0)];
265 }
266
271 template <class D>
273 {
275 return (*this)[size() - 1];
276 }
277
281 template <class D>
283 {
284 return cbegin();
285 }
286
291 template <class D>
293 {
294 return cend();
295 }
296
302 template <class D>
304 {
305 return const_iterator(this->derived_cast().value_cbegin(), bitmap_begin());
306 }
307
313 template <class D>
315 {
316 return const_iterator(this->derived_cast().value_cend(), bitmap_end());
317 }
318
324 template <class D>
326 {
327 return crbegin();
328 }
329
335 template <class D>
337 {
338 return crend();
339 }
340
347 template <class D>
352
360 template <class D>
365
370 template <class D>
375
380 template <class D>
382 {
383 return const_value_range(this->derived_cast().value_cbegin(), this->derived_cast().value_cend());
384 }
385
386 template <class D>
388 : m_proxy(std::move(proxy))
389 {
390 }
391
392 template <class D>
394 {
395 return m_proxy;
396 }
397
398 template <class D>
400 {
401 return m_proxy;
402 }
403
404 template <class D>
410
411 template <class D>
413 {
414 return sparrow::next(this->derived_cast().get_bitmap().cbegin(), get_arrow_proxy().offset());
415 }
416
417 template <class D>
422
423 template <class D>
428
429 template <class D>
431 {
432 return bitmap_end();
433 }
434
435 template <class D>
437 {
438 SPARROW_ASSERT_TRUE(start <= end);
439 return D{get_arrow_proxy().slice(start, end)};
440 }
441
442 template <class D>
444 {
445 SPARROW_ASSERT_TRUE(start <= end);
446 return D{get_arrow_proxy().slice_view(start, end)};
447 }
448
457 template <class D>
459 {
460 return std::ranges::equal(lhs, rhs);
461 }
462}
463
464#if defined(__cpp_lib_format)
465
466template <typename D>
467 requires std::derived_from<D, sparrow::array_crtp_base<D>>
468struct std::formatter<D>
469{
470 constexpr auto parse(std::format_parse_context& ctx)
471 {
472 return ctx.begin(); // Simple implementation
473 }
474
475 auto format(const D& ar, std::format_context& ctx) const
476 {
477 const auto& proxy = ar.get_arrow_proxy();
478 std::string type;
479 if (proxy.dictionary())
480 {
481 std::format_to(ctx.out(), "Dictionary<{}>", proxy.dictionary()->data_type());
482 }
483 else
484 {
485 std::format_to(ctx.out(), "{}", proxy.data_type());
486 }
487 std::format_to(ctx.out(), " [name={} | size={}] <", ar.name().value_or("nullptr"), proxy.length());
488
489 std::for_each(
490 ar.cbegin(),
491 std::prev(ar.cend()),
492 [&ctx](const auto& value)
493 {
494 std::format_to(ctx.out(), "{}, ", value);
495 }
496 );
497 return std::format_to(ctx.out(), "{}>", ar.back());
498 }
499};
500
501template <typename D>
502 requires std::derived_from<D, sparrow::array_crtp_base<D>>
503std::ostream& operator<<(std::ostream& os, const D& value)
504{
505 os << std::format("{}", value);
506 return os;
507}
508
509#endif
Base class defining common immutable interface for arrays with a bitmap.
D slice_view(size_type start, size_type end) const
Slices the array to keep only the elements between the given start and end.
array_crtp_base & operator=(const array_crtp_base &)=default
const_reverse_iterator rend() const
Returns a reverse iterator to the element following the last element of the reversed array.
const_reverse_iterator crend() const
Returns a reverse iterator to the element following the last element of the reversed array.
typename inner_types::const_value_iterator const_value_iterator
const_reference back() const
Returns a constant reference to the last element in the container.
array_crtp_base(array_crtp_base &&) noexcept=default
bitmap_type::const_reference bitmap_const_reference
std::ranges::subrange< const_value_iterator > const_value_range
bitmap_type::iterator bitmap_iterator
bool empty() const
Checks if the array has no element, i.e.
const_reference operator[](size_type i) const
Returns a constant reference to the element at the specified position in the array.
const_value_range values() const
Returns the raw values of the array (i.e.
const_reference front() const
Returns a constant reference to the first element in the container.
arrow_proxy & get_arrow_proxy()
nullable< inner_const_reference, bitmap_const_reference > const_reference
const_bitmap_iterator bitmap_end() const
const_bitmap_range bitmap() const
Returns the validity bitmap of the array (i.e.
typename inner_types::iterator_tag iterator_tag
const_bitmap_iterator bitmap_cend() const
std::ranges::subrange< const_bitmap_iterator > const_bitmap_range
const_bitmap_iterator bitmap_cbegin() const
friend class detail::array_access
const_iterator begin() const
Returns a constant iterator to the first element of the array.
typename inner_types::bitmap_type bitmap_type
const_iterator end() const
Returns a constant iterator to the element following the last element of the array.
bitmap_type::const_iterator const_bitmap_iterator
array_crtp_base(const array_crtp_base &)=default
typename inner_types::inner_const_reference inner_const_reference
size_type size() const
Returns the number of elements in the array.
D slice(size_type start, size_type end) const
Slices the array to keep only the elements between the given start and end.
nullable< inner_value_type > value_type
const_iterator cbegin() const
Returns a constant iterator to the first element of the array.
std::ptrdiff_t difference_type
layout_iterator< iterator_types > const_iterator
std::optional< std::string_view > name() const
const_bitmap_iterator bitmap_begin() const
array_crtp_base< D > self_type
std::reverse_iterator< const_iterator > const_reverse_iterator
const_reverse_iterator rbegin() const
Returns a constant reverse iterator to the first element of the reversed array.
const_reverse_iterator crbegin() const
Returns a constant reverse iterator to the first element of the reversed array.
bitmap_const_reference has_value(size_type i) const
array_inner_types< derived_type > inner_types
const_iterator cend() const
Returns a constant iterator to the element following the last element of the array.
const_reference at(size_type i) const
Returns a constant reference to the element at the specified position in the array with bounds checki...
std::optional< key_value_view > metadata() const
typename inner_types::inner_value_type inner_value_type
Proxy class over ArrowArray and ArrowSchema.
Base class for CRTP base classes.
Definition crtp_base.hpp:29
derived_type & derived_cast()
Definition crtp_base.hpp:39
This class represents a view to a dynamic size sequence of bits.
Layout iterator class.
base_type::const_reference const_reference
bitmap_type::const_reference bitmap_const_reference
base_type::const_iterator const_iterator
bitmap_reference has_value(size_type i)
base_type::const_bitmap_range const_bitmap_range
iterator end()
Returns a iterator to the element following the last element of the array.
The nullable class models a value or a reference that can be "null", or missing, like values traditio...
Definition nullable.hpp:281
Concept for iterator types.
#define SPARROW_ASSERT_TRUE(expr__)
SPARROW_API bool operator==(const array &lhs, const array &rhs)
Compares the content of two arrays.
constexpr InputIt next(InputIt it, Distance n)
Definition iterator.hpp:503
std::ostream & operator<<(std::ostream &os, const sparrow::nullval_t &)
Definition nullable.hpp:933
self_type::const_reference reference
self_type::const_bitmap_iterator bitmap_iterator
self_type::const_value_iterator value_iterator
Base class for array_inner_types specialization.
dynamic_bitset_view< std::uint8_t > bitmap_type
Traits class that must be specialized by array classes inheriting from array_crtp_base.