Expression Templates Library (ETL)
scalar.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 #include <concepts>
16 namespace etl {
17 
21 template <typename T>
22 struct scalar {
23  using value_type = T;
24 
28  template <typename V = default_vec>
29  using vec_type = typename V::template vec_type<T>;
30 
31  const T value;
32 
37  explicit constexpr scalar(T v) : value(v) {}
38 
43  template <std::convertible_to<T> C>
44  explicit constexpr scalar(C c) : value(static_cast<T>(c)) {}
45 
51  constexpr T operator[](size_t d) const noexcept {
52  return (void)d, value;
53  }
54 
61  constexpr T read_flat(size_t d) const noexcept {
62  return (void)d, value;
63  }
64 
71  template <typename V = default_vec>
72  vec_type<V> load(size_t d) const noexcept {
73  return (void)d, V::set(value);
74  }
75 
82  template <typename V = default_vec>
83  vec_type<V> loadu(size_t d) const noexcept {
84  return (void)d, V::set(value);
85  }
86 
92  template <size_c... S>
93  constexpr T operator()(__attribute__((unused)) S... args) const noexcept {
94  return value;
95  }
96 
101  template <typename E>
102  constexpr bool alias(const E& /*rhs*/) const noexcept {
103  return false;
104  }
105 
106  // Assignment functions
107 
112  template <typename L>
113  void assign_to(L&& lhs) const {
114  std_assign_evaluate(*this, std::forward<L>(lhs));
115  }
116 
121  template <typename L>
122  void assign_add_to(L&& lhs) const {
123  std_add_evaluate(*this, std::forward<L>(lhs));
124  }
125 
130  template <typename L>
131  void assign_sub_to(L&& lhs) const {
132  std_sub_evaluate(*this, std::forward<L>(lhs));
133  }
134 
139  template <typename L>
140  void assign_mul_to(L&& lhs) const {
141  std_mul_evaluate(*this, std::forward<L>(lhs));
142  }
143 
148  template <typename L>
149  void assign_div_to(L&& lhs) const {
150  std_div_evaluate(*this, std::forward<L>(lhs));
151  }
152 
157  template <typename L>
158  void assign_mod_to(L&& lhs) const {
159  std_mod_evaluate(*this, std::forward<L>(lhs));
160  }
161 
162  // Internals
163 
168  template <typename V>
169  void visit([[maybe_unused]] V&& visitor) const {}
170 
175  template <typename Y>
176  decltype(auto) gpu_compute_hint([[maybe_unused]] Y& y) const {
177  // TODO Maybe make a full vector with the hint
178 
180 
181  t1.resize_scalar();
182  t1.ensure_gpu_allocated();
183 
184 #ifdef ETL_CUDA
185  cuda_check(cudaMemcpy(t1.gpu_memory(), &value, 1 * sizeof(T), cudaMemcpyHostToDevice));
186 #endif
187 
188  return t1;
189  }
190 
195  template <typename Y>
196  decltype(auto) gpu_compute(Y& y) const {
197  y.ensure_gpu_allocated();
198 
199 #ifdef ETL_CUDA
200  cuda_check(cudaMemcpy(y.gpu_memory(), &value, etl::size(y) * sizeof(T), cudaMemcpyHostToDevice));
201 #endif
202 
203  return y;
204  }
205 
210  void ensure_cpu_up_to_date() const {
211  // Nothing to ensure
212  }
213 
218  void ensure_gpu_up_to_date() const {
219  // Nothing to ensure
220  }
221 
228  friend std::ostream& operator<<(std::ostream& os, const scalar& s) {
229  return os << s.value;
230  }
231 };
232 
236 template <typename T>
237 struct etl_traits<etl::scalar<T>> {
238  using value_type = T;
239 
240  static constexpr bool is_etl = true;
241  static constexpr bool is_transformer = false;
242  static constexpr bool is_view = false;
243  static constexpr bool is_magic_view = false;
244  static constexpr bool is_fast = true;
245  static constexpr bool is_value = false;
246  static constexpr bool is_direct = false;
247  static constexpr bool is_linear = true;
248  static constexpr bool is_thread_safe = true;
249  static constexpr bool is_generator = true;
250  static constexpr bool is_temporary = false;
251  static constexpr bool is_padded = true;
252  static constexpr bool is_aligned = true;
253  static constexpr bool gpu_computable = is_gpu_t<value_type> && cuda_enabled;
254  static constexpr order storage_order = order::RowMajor;
255 
261  template <vector_mode_t VV>
262  static constexpr bool vectorizable = true;
263 
267  static constexpr size_t size() {
268  return 0;
269  }
270 
274  static constexpr size_t dimensions() {
275  return 0;
276  }
277 
282  static constexpr int complexity() noexcept {
283  return 4;
284  }
285 };
286 
287 } //end of namespace etl
void assign_div_to(L &&lhs) const
Divide the given left-hand-side expression.
Definition: scalar.hpp:149
auto s(T &&value)
Force the evaluation of the given expression.
Definition: stop.hpp:18
void std_assign_evaluate(Expr &&expr, Result &&result)
Evaluation of the expr into result.
Definition: evaluator.hpp:1176
constexpr scalar(T v)
Builds a new scalar \þaram v The scalar value.
Definition: scalar.hpp:37
void assign_mul_to(L &&lhs) const
Multiply the given left-hand-side expression.
Definition: scalar.hpp:140
constexpr bool is_magic_view
Traits indicating if the given ETL type is a magic view expression.
Definition: traits.hpp:311
const T value
The scalar value.
Definition: scalar.hpp:31
order
Storage order of a matrix.
Definition: order.hpp:15
constexpr T read_flat(size_t d) const noexcept
Returns the value at the given index This function never alters the state of the container.
Definition: scalar.hpp:61
constexpr bool cuda_enabled
Indicates if CUDA is available.
Definition: config.hpp:94
void resize_scalar()
Resize the matrix as a scalar value.
Definition: gpu_dyn.hpp:307
void assign_sub_to(L &&lhs) const
Sub from the given left-hand-side expression.
Definition: scalar.hpp:131
constexpr bool is_fast
Traits to test if the given ETL expresion type is fast (sizes known at compile-time) ...
Definition: traits.hpp:588
decltype(auto) gpu_compute_hint([[maybe_unused]] Y &y) const
Return a GPU computed version of this expression.
Definition: scalar.hpp:176
Traits to get information about ETL types.
Definition: tmp.hpp:68
Root namespace for the ETL library.
Definition: adapter.hpp:15
typename V::template vec_type< T > vec_type
Definition: scalar.hpp:29
void assign_to(L &&lhs) const
Assign to the given left-hand-side expression.
Definition: scalar.hpp:113
constexpr T operator()(__attribute__((unused)) S... args) const noexcept
Returns the value at the position (args...)
Definition: scalar.hpp:93
static constexpr size_t size()
Return the size of the expression.
Definition: scalar.hpp:267
T value_type
The value type.
Definition: scalar.hpp:23
void assign_mod_to(L &&lhs) const
Modulo the given left-hand-side expression.
Definition: scalar.hpp:158
static constexpr size_t dimensions()
Return the number of dimensions of the expression.
Definition: scalar.hpp:274
void std_mod_evaluate(Expr &&expr, Result &&result)
Compound modulo evaluation of the expr into result.
Definition: evaluator.hpp:1271
void std_mul_evaluate(Expr &&expr, Result &&result)
Compound multiply evaluation of the expr into result.
Definition: evaluator.hpp:1233
constexpr T operator[](size_t d) const noexcept
Returns the element at the given index.
Definition: scalar.hpp:51
constexpr bool is_transformer
Traits indicating if the given ETL type is a transformer expression.
Definition: traits.hpp:297
Represents a scalar value.
Definition: concepts_base.hpp:19
decltype(auto) gpu_compute(Y &y) const
Return a GPU computed version of this expression.
Definition: scalar.hpp:196
void visit([[maybe_unused]] V &&visitor) const
Apply the given visitor to this expression and its descendants.
Definition: scalar.hpp:169
T value_type
The value type of the expression.
Definition: scalar.hpp:238
constexpr size_t size(const E &expr) noexcept
Returns the size of the given ETL expression.
Definition: helpers.hpp:108
constexpr bool is_view
Traits indicating if the given ETL type is a view expression.
Definition: traits.hpp:304
vec_type< V > load(size_t d) const noexcept
Load several elements of the matrix at once.
Definition: scalar.hpp:72
static constexpr int complexity() noexcept
Estimate the complexity of computation.
Definition: scalar.hpp:282
vec_type< V > loadu(size_t d) const noexcept
Load several elements of the matrix at once.
Definition: scalar.hpp:83
void std_sub_evaluate(Expr &&expr, Result &&result)
Compound subtract evaluation of the expr into result.
Definition: evaluator.hpp:1214
constexpr bool alias(const E &) const noexcept
Indicate if the expression aliases with the given expression.
Definition: scalar.hpp:102
constexpr scalar(C c)
Builds a new scalar from a convertible type \þaram v The scalar value.
Definition: scalar.hpp:44
constexpr bool is_thread_safe
Traits to test if the given ETL expresion type is thread safe.
Definition: traits.hpp:687
void ensure_gpu_up_to_date() const
Copy back from the GPU to the expression memory if necessary.
Definition: scalar.hpp:218
void assign_add_to(L &&lhs) const
Add to the given left-hand-side expression.
Definition: scalar.hpp:122
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: scalar.hpp:210
GPU special Matrix with run-time fixed dimensions.
Definition: gpu_dyn.hpp:25
void std_div_evaluate(Expr &&expr, Result &&result)
Compound divide evaluation of the expr into result.
Definition: evaluator.hpp:1252
Row-Major storage.
friend std::ostream & operator<<(std::ostream &os, const scalar &s)
Prints a scalar value to the given stream.
Definition: scalar.hpp:228
void std_add_evaluate(Expr &&expr, Result &&result)
Compound add evaluation of the expr into result.
Definition: evaluator.hpp:1195