Expression Templates Library (ETL)
memory_slice_view.hpp
Go to the documentation of this file.
1 //=======================================================================
2 // Copyright (c) 2014-2023 Baptiste Wicht
3 // Distributed under the terms of the MIT License.
4 // (See accompanying file LICENSE or copy at
5 // http://opensource.org/licenses/MIT)
6 //=======================================================================
7 
13 #pragma once
14 
15 namespace etl {
16 
21 template <typename T, bool Aligned>
22 struct memory_slice_view {
23  using sub_type = T;
26  using const_memory_type = const value_type*;
29 
30 private:
31  T sub;
32  const size_t first;
33  const size_t last;
34 
35  friend struct etl_traits<memory_slice_view>;
36 
37 public:
41  template <typename V = default_vec>
42  using vec_type = typename V::template vec_type<value_type>;
43 
50  memory_slice_view(sub_type sub, size_t first, size_t last) : sub(sub), first(first), last(last) {}
51 
57  const_return_type operator[](size_t j) const {
58  return sub[first + j];
59  }
60 
66  return_type operator[](size_t j) {
67  return sub[first + j];
68  }
69 
76  value_type read_flat(size_t j) const noexcept {
77  return sub[first + j];
78  }
79 
86  template <typename V = default_vec>
87  auto load(size_t x) const noexcept {
88  if constexpr (Aligned) {
89  return sub.template load<V>(x + first);
90  } else {
91  return sub.template loadu<V>(x + first);
92  }
93  }
94 
101  template <typename V = default_vec>
102  auto loadu(size_t x) const noexcept {
103  return sub.template loadu<V>(x + first);
104  }
105 
112  template <typename V = default_vec>
113  void store(vec_type<V> in, size_t i) noexcept {
114  if constexpr (Aligned) {
115  sub.template store<V>(in, first + i);
116  } else {
117  sub.template storeu<V>(in, first + i);
118  }
119  }
120 
127  template <typename V = default_vec>
128  void storeu(vec_type<V> in, size_t i) noexcept {
129  sub.template storeu<V>(in, first + i);
130  }
131 
138  template <typename V = default_vec>
139  void stream(vec_type<V> in, size_t i) noexcept {
140  if constexpr (Aligned) {
141  sub.template stream<V>(in, first + i);
142  } else {
143  sub.template storeu<V>(in, first + i);
144  }
145  }
146 
152  template <typename E>
153  bool alias(const E& rhs) const noexcept {
154  return sub.alias(rhs);
155  }
156 
162  return sub.memory_start() + first;
163  }
164 
169  const_memory_type memory_start() const noexcept {
170  return sub.memory_start() + first;
171  }
172 
177  memory_type memory_end() noexcept {
178  return sub.memory_start() + last;
179  }
180 
185  const_memory_type memory_end() const noexcept {
186  return sub.memory_start() + last;
187  }
188 
189  // Assignment functions
190 
195  template <typename L>
196  void assign_to(L&& lhs) const {
197  std_assign_evaluate(*this, std::forward<L>(lhs));
198  }
199 
204  template <typename L>
205  void assign_add_to(L&& lhs) const {
206  std_add_evaluate(*this, std::forward<L>(lhs));
207  }
208 
213  template <typename L>
214  void assign_sub_to(L&& lhs) const {
215  std_sub_evaluate(*this, std::forward<L>(lhs));
216  }
217 
222  template <typename L>
223  void assign_mul_to(L&& lhs) const {
224  std_mul_evaluate(*this, std::forward<L>(lhs));
225  }
226 
231  template <typename L>
232  void assign_div_to(L&& lhs) const {
233  std_div_evaluate(*this, std::forward<L>(lhs));
234  }
235 
240  template <typename L>
241  void assign_mod_to(L&& lhs) const {
242  std_mod_evaluate(*this, std::forward<L>(lhs));
243  }
244 
245  // Internals
246 
251  void visit(detail::evaluator_visitor& visitor) const {
252  sub.visit(visitor);
253  }
254 
259  void ensure_cpu_up_to_date() const {
260  // The sub value must be ensured
261  sub.ensure_cpu_up_to_date();
262  }
263 
268  void ensure_gpu_up_to_date() const {
269  // The sub value must be ensured
270  sub.ensure_gpu_up_to_date();
271  }
272 };
273 
277 template <typename T, bool Aligned>
278 struct etl_traits<etl::memory_slice_view<T, Aligned>> {
280  using sub_expr_t = std::decay_t<T>;
282 
283  static constexpr bool is_etl = true;
284  static constexpr bool is_transformer = false;
285  static constexpr bool is_view = true;
286  static constexpr bool is_magic_view = false;
287  static constexpr bool is_fast = false;
288  static constexpr bool is_linear = etl_traits<sub_expr_t>::is_linear;
290  static constexpr bool is_value = false;
291  static constexpr bool is_direct = etl_traits<sub_expr_t>::is_direct;
292  static constexpr bool is_generator = false;
293  static constexpr bool is_padded = false;
294  static constexpr bool is_aligned = Aligned;
295  static constexpr bool is_temporary = etl_traits<sub_expr_t>::is_temporary;
296  static constexpr bool gpu_computable = false;
297  static constexpr order storage_order = etl_traits<sub_expr_t>::storage_order;
298 
304  template <vector_mode_t V>
305  static constexpr bool vectorizable = etl_traits<sub_expr_t>::template vectorizable<V>;
306 
312  static size_t size(const expr_t& v) {
313  return v.last - v.first;
314  }
315 
322  static size_t dim(const expr_t& v, [[maybe_unused]] size_t d) {
323  return v.last - v.first;
324  }
325 
330  static constexpr size_t dimensions() {
331  return 1;
332  }
333 
338  static constexpr int complexity() noexcept {
339  return -1;
340  }
341 };
342 
350 template <bool Aligned = false, etl_expr E>
351 auto memory_slice(E&& value, size_t first, size_t last) -> detail::identity_helper<E, memory_slice_view<detail::build_identity_type<E>, Aligned>> {
353 }
354 
355 } //end of namespace etl
const_memory_type memory_start() const noexcept
Returns a pointer to the first element in memory.
Definition: memory_slice_view.hpp:169
void assign_mul_to(L &&lhs) const
Multiply the given left-hand-side expression.
Definition: memory_slice_view.hpp:223
void assign_sub_to(L &&lhs) const
Sub from the given left-hand-side expression.
Definition: memory_slice_view.hpp:214
void visit(detail::evaluator_visitor &visitor) const
Apply the given visitor to this expression and its descendants.
Definition: memory_slice_view.hpp:251
void stream(vec_type< V > in, size_t i) noexcept
Store several elements in the matrix at once, using non-temporal store.
Definition: memory_slice_view.hpp:139
static size_t size(const expr_t &v)
Returns the size of the given expression.
Definition: memory_slice_view.hpp:312
void storeu(vec_type< V > in, size_t i) noexcept
Store several elements in the matrix at once.
Definition: memory_slice_view.hpp:128
void std_assign_evaluate(Expr &&expr, Result &&result)
Evaluation of the expr into result.
Definition: evaluator.hpp:1176
void assign_add_to(L &&lhs) const
Add to the given left-hand-side expression.
Definition: memory_slice_view.hpp:205
constexpr bool is_magic_view
Traits indicating if the given ETL type is a magic view expression.
Definition: traits.hpp:311
auto loadu(size_t x) const noexcept
Load several elements of the expression at once.
Definition: memory_slice_view.hpp:102
memory_slice_view(sub_type sub, size_t first, size_t last)
Construct a new memory_slice_view over the given sub expression.
Definition: memory_slice_view.hpp:50
void ensure_gpu_up_to_date() const
Copy back from the GPU to the expression memory if necessary.
Definition: memory_slice_view.hpp:268
order
Storage order of a matrix.
Definition: order.hpp:15
static constexpr int complexity() noexcept
Estimate the complexity of computation.
Definition: memory_slice_view.hpp:338
View that shows a slice of an expression.
Definition: expr_fwd.hpp:74
memory_type memory_start() noexcept
Returns a pointer to the first element in memory.
Definition: memory_slice_view.hpp:161
std::conditional_t< std::is_lvalue_reference_v< S >, const value_t< T > &, value_t< T > > const_return_helper
Definition: traits.hpp:872
An unary expression.
Definition: unary_expr.hpp:126
constexpr bool is_fast
Traits to test if the given ETL expresion type is fast (sizes known at compile-time) ...
Definition: traits.hpp:588
static constexpr size_t dimensions()
Returns the number of expressions for this type.
Definition: memory_slice_view.hpp:330
void ensure_cpu_up_to_date() const
Ensures that the GPU memory is allocated and that the GPU memory is up to date (to undefined value)...
Definition: memory_slice_view.hpp:259
value_t< sub_type > value_type
The value contained in the expression.
Definition: memory_slice_view.hpp:24
return_type operator[](size_t j)
Returns the element at the given index.
Definition: memory_slice_view.hpp:66
Traits to get information about ETL types.
Definition: tmp.hpp:68
const_return_helper< sub_type, decltype(std::declval< sub_type >()[0])> const_return_type
The const type return by the view.
Definition: memory_slice_view.hpp:28
Root namespace for the ETL library.
Definition: adapter.hpp:15
typename V::template vec_type< value_type > vec_type
The vectorization type for V.
Definition: memory_slice_view.hpp:42
std::conditional_t< std::is_const_v< std::remove_reference_t< S > >, const value_t< T > &, std::conditional_t< std::is_lvalue_reference_v< S > &&!std::is_const_v< T >, value_t< T > &, value_t< T > >> return_helper
Definition: traits.hpp:866
const_memory_type memory_end() const noexcept
Returns a pointer to the past-the-end element in memory.
Definition: memory_slice_view.hpp:185
auto load(size_t x) const noexcept
Load several elements of the expression at once.
Definition: memory_slice_view.hpp:87
const_return_type operator[](size_t j) const
Returns the element at the given index.
Definition: memory_slice_view.hpp:57
static size_t dim(const expr_t &v, [[maybe_unused]] size_t d)
Returns the dth dimension of the given expression.
Definition: memory_slice_view.hpp:322
Visitor to perform local evaluation when necessary.
Definition: eval_visitors.hpp:23
typename etl_traits< sub_expr_t >::value_type value_type
The value type.
Definition: memory_slice_view.hpp:281
void assign_div_to(L &&lhs) const
Divide the given left-hand-side expression.
Definition: memory_slice_view.hpp:232
void std_mod_evaluate(Expr &&expr, Result &&result)
Compound modulo evaluation of the expr into result.
Definition: evaluator.hpp:1271
memory_type memory_end() noexcept
Returns a pointer to the past-the-end element in memory.
Definition: memory_slice_view.hpp:177
void assign_to(L &&lhs) const
Assign to the given left-hand-side expression.
Definition: memory_slice_view.hpp:196
void std_mul_evaluate(Expr &&expr, Result &&result)
Compound multiply evaluation of the expr into result.
Definition: evaluator.hpp:1233
constexpr bool is_transformer
Traits indicating if the given ETL type is a transformer expression.
Definition: traits.hpp:297
const value_type * const_memory_type
The const memory access type.
Definition: memory_slice_view.hpp:26
void assign_mod_to(L &&lhs) const
Modulo the given left-hand-side expression.
Definition: memory_slice_view.hpp:241
constexpr bool is_view
Traits indicating if the given ETL type is a view expression.
Definition: traits.hpp:304
value_type * memory_type
The memory acess type.
Definition: memory_slice_view.hpp:25
void store(vec_type< V > in, size_t i) noexcept
Store several elements in the matrix at once.
Definition: memory_slice_view.hpp:113
T sub_type
The sub type.
Definition: memory_slice_view.hpp:23
auto memory_slice(E &&value, size_t first, size_t last) -> detail::identity_helper< E, memory_slice_view< detail::build_identity_type< E >, Aligned >>
Returns view representing a memory slice view of the given expression.
Definition: memory_slice_view.hpp:351
void std_sub_evaluate(Expr &&expr, Result &&result)
Compound subtract evaluation of the expr into result.
Definition: evaluator.hpp:1214
constexpr bool is_thread_safe
Traits to test if the given ETL expresion type is thread safe.
Definition: traits.hpp:687
value_type read_flat(size_t j) const noexcept
Returns the value at the given index This function never has side effects.
Definition: memory_slice_view.hpp:76
std::decay_t< T > sub_expr_t
The sub expression type.
Definition: memory_slice_view.hpp:280
bool alias(const E &rhs) const noexcept
Test if this expression aliases with the given expression.
Definition: memory_slice_view.hpp:153
typename decay_traits< E >::value_type value_t
Traits to extract the value type out of an ETL type.
Definition: tmp.hpp:81
void std_div_evaluate(Expr &&expr, Result &&result)
Compound divide evaluation of the expr into result.
Definition: evaluator.hpp:1252
return_helper< sub_type, decltype(std::declval< sub_type >()[0])> return_type
The type returned by the view.
Definition: memory_slice_view.hpp:27
void std_add_evaluate(Expr &&expr, Result &&result)
Compound add evaluation of the expr into result.
Definition: evaluator.hpp:1195