This repository was archived by the owner on Jul 7, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy patharray.hpp
128 lines (101 loc) · 4.03 KB
/
array.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
// Copyright 2022 The Jule Programming Language.
// Use of this source code is governed by a BSD 3-Clause
// license that can be found in the LICENSE file.
#ifndef __JULE_ARRAY_HPP
#define __JULE_ARRAY_HPP
#include <initializer_list>
#include <sstream>
#include <ostream>
#include "error.hpp"
#include "panic.hpp"
#include "types.hpp"
#include "slice.hpp"
namespace jule {
// Built-in array type.
template<typename Item, const jule::Uint N>
struct Array;
template<typename Item, const jule::Uint N>
struct Array {
public:
mutable std::array<Item, N> buffer{};
Array<Item, N>(void) noexcept {}
Array<Item, N>(const std::initializer_list<Item> &src) noexcept {
const auto src_begin{ src.begin() };
for (jule::Int index{ 0 }; index < src.size(); ++index)
this->buffer[index] = *(Item*)(src_begin+index);
}
typedef Item *Iterator;
typedef const Item *ConstIterator;
inline constexpr
Iterator begin(void) noexcept
{ return &this->buffer[0]; }
inline constexpr
ConstIterator begin(void) const noexcept
{ return &this->buffer[0]; }
inline constexpr
Iterator end(void) noexcept
{ return &this->buffer[N]; }
inline constexpr
ConstIterator end(void) const noexcept
{ return &this->_buffer[N]; }
inline jule::Slice<Item> slice(const jule::Int &start,
const jule::Int &end) const noexcept {
if (start < 0 || end < 0 || start > end || end > this->len()) {
std::stringstream sstream;
__JULEC_WRITE_ERROR_SLICING_INDEX_OUT_OF_RANGE(
sstream, start, end );
jule::panic(sstream.str().c_str());
} else if (start == end)
return jule::Slice<Item>();
const jule::Int n{ end-start };
jule::Slice<Item> slice{ jule::Slice<Item>::alloc(n) };
for (jule::Int counter{ 0 }; counter < n; ++counter)
slice[counter] = this->buffer[start+counter];
return slice;
}
inline jule::Slice<Item> slice(const jule::Int &start) const noexcept
{ return this->slice(start, this->len()); }
inline jule::Slice<Item> slice(void) const noexcept
{ return this->slice(0, this->len()); }
inline constexpr
jule::Int len(void) const noexcept
{ return N; }
inline constexpr
jule::Bool empty(void) const noexcept
{ return N == 0; }
inline constexpr
jule::Bool operator==(const jule::Array<Item, N> &src) const noexcept
{ return this->buffer == src.buffer; }
inline constexpr
jule::Bool operator!=(const jule::Array<Item, N> &src) const noexcept
{ return !this->operator==(src); }
Item &operator[](const jule::Int &index) const {
if (this->empty() || index < 0 || this->len() <= index) {
std::stringstream sstream;
__JULEC_WRITE_ERROR_INDEX_OUT_OF_RANGE(sstream, index);
jule::panic(sstream.str().c_str());
}
return this->buffer[index];
}
Item &operator[](const jule::Int &index) {
if (this->empty() || index < 0 || this->len() <= index) {
std::stringstream sstream;
__JULEC_WRITE_ERROR_INDEX_OUT_OF_RANGE(sstream, index);
jule::panic(sstream.str().c_str());
}
return this->buffer[index];
}
friend std::ostream &operator<<(std::ostream &stream,
const jule::Array<Item, N> &src) noexcept {
stream << '[';
for (jule::Int index{0}; index < src.len();) {
stream << src.buffer[index++];
if (index < src.len())
stream << " ";
}
stream << ']';
return stream;
}
};
} // namespace jule
#endif // #ifndef __JULE_ARRAY_HPP