• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2025 Huawei Device Co., Ltd.
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 implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #ifndef RUNTIME_INCLUDE_TAIHE_VECTOR_HPP_
16 #define RUNTIME_INCLUDE_TAIHE_VECTOR_HPP_
17 // NOLINTBEGIN
18 
19 #include <taihe/common.hpp>
20 
21 #include <algorithm>
22 #include <utility>
23 
24 #define VEC_GROWTH_FACTOR 2
25 
26 namespace taihe {
27 template <typename T>
28 struct vector_view;
29 
30 template <typename T>
31 struct vector;
32 
33 template <typename T>
34 struct vector_view {
35 public:
36     using value_type = T;
37     using size_type = std::size_t;
38     using reference = T &;
39     using pointer = T *;
40 
reservetaihe::vector_view41     void reserve(std::size_t cap) const
42     {
43         if (cap < m_handle->len) {
44             return;
45         }
46         m_handle->cap = cap;
47         m_handle->buffer = reinterpret_cast<T *>(realloc(m_handle->buffer, sizeof(T) * cap));
48     }
49 
sizetaihe::vector_view50     std::size_t size() const noexcept
51     {
52         return m_handle->len;
53     }
54 
emptytaihe::vector_view55     bool empty() const noexcept
56     {
57         return m_handle->len == 0;
58     }
59 
capacitytaihe::vector_view60     std::size_t capacity() const noexcept
61     {
62         return m_handle->cap;
63     }
64 
65     template <typename... Args>
emplace_backtaihe::vector_view66     T &emplace_back(Args &&...args) const
67     {
68         std::size_t required_cap = m_handle->len + 1;
69         if (required_cap > m_handle->cap) {
70             this->reserve(std::max(required_cap, m_handle->cap * VEC_GROWTH_FACTOR));
71         }
72         T *location = &m_handle->buffer[m_handle->len];
73         new (location) T {std::forward<Args>(args)...};
74         ++m_handle->len;
75         return *location;
76     }
77 
push_backtaihe::vector_view78     T &push_back(T &&value) const
79     {
80         return emplace_back(std::move(value));
81     }
82 
push_backtaihe::vector_view83     T &push_back(T const &value) const
84     {
85         return emplace_back(value);
86     }
87 
operator []taihe::vector_view88     T &operator[](std::size_t index) const
89     {
90         return m_handle->buffer[index];
91     }
92 
pop_backtaihe::vector_view93     void pop_back() const
94     {
95         if (m_handle->len == 0) {
96             return;
97         }
98         std::destroy_at(&m_handle->buffer[m_handle->len]);
99         --m_handle->len;
100     }
101 
cleartaihe::vector_view102     void clear() const noexcept
103     {
104         for (std::size_t i = 0; i < m_handle->len; i++) {
105             std::destroy_at(&m_handle->buffer[i]);
106         }
107         m_handle->len = 0;
108     }
109 
110     using iterator = T *;
111     using const_iterator = T const *;
112 
begintaihe::vector_view113     iterator begin() const
114     {
115         return m_handle->buffer;
116     }
117 
endtaihe::vector_view118     iterator end() const
119     {
120         return m_handle->buffer + m_handle->len;
121     }
122 
cbegintaihe::vector_view123     const_iterator cbegin() const
124     {
125         return begin();
126     }
127 
cendtaihe::vector_view128     const_iterator cend() const
129     {
130         return end();
131     }
132 
133 protected:
134     struct data_t {
135         TRefCount count;
136         std::size_t cap;
137         T *buffer;
138         std::size_t len;
139     } *m_handle;
140 
vector_viewtaihe::vector_view141     explicit vector_view(data_t *handle) : m_handle(handle) {}
142 
143     friend struct vector<T>;
144 
145     friend struct std::hash<vector<T>>;
146 
operator ==(vector_view lhs,vector_view rhs)147     friend bool operator==(vector_view lhs, vector_view rhs)
148     {
149         return lhs.m_handle == rhs.m_handle;
150     }
151 };
152 
153 template <typename T>
154 struct vector : vector_view<T> {
155     using typename vector_view<T>::data_t;
156     using vector_view<T>::m_handle;
157 
vectortaihe::vector158     explicit vector(std::size_t cap = 0) : vector(reinterpret_cast<data_t *>(malloc(sizeof(data_t))))
159     {
160         tref_set(&m_handle->count, 1);
161         m_handle->cap = cap;
162         m_handle->buffer = reinterpret_cast<T *>(malloc(sizeof(T) * cap));
163         m_handle->len = 0;
164     }
165 
vectortaihe::vector166     vector(vector<T> &&other) noexcept : vector(other.m_handle)
167     {
168         other.m_handle = nullptr;
169     }
170 
vectortaihe::vector171     vector(vector<T> const &other) : vector(other.m_handle)
172     {
173         if (m_handle) {
174             tref_inc(&m_handle->count);
175         }
176     }
177 
vectortaihe::vector178     vector(vector_view<T> const &other) : vector(other.m_handle)
179     {
180         if (m_handle) {
181             tref_inc(&m_handle->count);
182         }
183     }
184 
operator =taihe::vector185     vector &operator=(vector other)
186     {
187         std::swap(this->m_handle, other.m_handle);
188         return *this;
189     }
190 
~vectortaihe::vector191     ~vector()
192     {
193         if (m_handle && tref_dec(&m_handle->count)) {
194             this->clear();
195             free(m_handle->buffer);
196             free(m_handle);
197         }
198     }
199 
200 private:
vectortaihe::vector201     explicit vector(data_t *handle) : vector_view<T>(handle) {}
202 };
203 
204 template <typename T>
205 struct as_abi<vector<T>> {
206     using type = void *;
207 };
208 
209 template <typename T>
210 struct as_abi<vector_view<T>> {
211     using type = void *;
212 };
213 
214 template <typename T>
215 struct as_param<vector<T>> {
216     using type = vector_view<T>;
217 };
218 }  // namespace taihe
219 
220 template <typename T>
221 struct std::hash<taihe::vector<T>> {
operator ()std::hash222     std::size_t operator()(taihe::vector_view<T> val) const noexcept
223     {
224         return reinterpret_cast<std::size_t>(val.m_handle);
225     }
226 };
227 
228 #ifdef VEC_GROWTH_FACTOR
229 #undef VEC_GROWTH_FACTOR
230 #endif
231 // NOLINTEND
232 #endif  // RUNTIME_INCLUDE_TAIHE_VECTOR_HPP_