Compadre 1.6.4
Loading...
Searching...
No Matches
Compadre_SolutionSet.hpp
Go to the documentation of this file.
1// @HEADER
2// *****************************************************************************
3// Compadre: COMpatible PArticle Discretization and REmap Toolkit
4//
5// Copyright 2018 NTESS and the Compadre contributors.
6// SPDX-License-Identifier: BSD-2-Clause
7// *****************************************************************************
8// @HEADER
9#ifndef _COMPADRE_SOLUTIONSET_HPP_
10#define _COMPADRE_SOLUTIONSET_HPP_
11
12#include "Compadre_Typedefs.hpp"
14#include <Kokkos_Core.hpp>
15
16namespace Compadre {
17
18//! All vairables and functionality related to the layout and storage of GMLS
19//! solutions (alpha values)
20template <typename memory_space = device_memory_space>
22
23 //! vector of user requested target operations
24 Kokkos::View<TargetOperation*, memory_space> _lro;
25
26 //! vector containing a mapping from a target functionals enum value to the its place in the list
27 //! of target functionals to be applied
28 Kokkos::View<int*, memory_space> _lro_lookup;
29
30 //! index for where this operation begins the for _alpha coefficients
31 Kokkos::View<int*, memory_space> _lro_total_offsets;
32
33 //! dimensions ^ rank of tensor of output for each target functional
34 Kokkos::View<int*, memory_space> _lro_output_tile_size;
35
36 //! dimensions ^ rank of tensor of output for each sampling functional
37 Kokkos::View<int*, memory_space> _lro_input_tile_size;
38
39 //! tensor rank of target functional (device)
40 Kokkos::View<int*, memory_space> _lro_output_tensor_rank;
41
42 //! tensor rank of sampling functional (device)
43 Kokkos::View<int*, memory_space> _lro_input_tensor_rank;
44
45 //! generated alpha coefficients (device)
46 Kokkos::View<double*, layout_right, memory_space> _alphas;
47
48 //! additional alpha coefficients due to constraints
50
51 //! maximum number of evaluation sites for each target (includes target site)
53
54 //! used for sizing P_target_row and the _alphas view
56
57 //! whether internal alpha values are valid (set externally on a solve)
59
60 //
61 // Redundant variables (already exist in GMLS class)
62 //
63
64 //! Accessor to get neighbor list data, offset data, and number of neighbors per target
66
67 //! generally the same as _polynomial_sampling_functional, but can differ if specified at
68 //! GMLS class instantiation
70
71 //! dimension of the problem, set at class instantiation only
73
74 //! dimension of the problem, set at class instantiation only. For manifolds, generally _global_dimensions-1
76
77 //! problem type for GMLS problem, can also be set to STANDARD for normal or MANIFOLD for manifold problems
79
80/** @name Constructors
81 */
82///@{
83
84 //! \brief Constructor for SolutionSet
85 SolutionSet(SamplingFunctional data_sampling_functional,
86 int dimensions,
87 int local_dimensions,
88 const ProblemType problem_type) :
93 _data_sampling_functional(data_sampling_functional),
94 _dimensions(dimensions),
95 _local_dimensions(local_dimensions),
96 _problem_type(problem_type) {}
97
99
100 //! \brief Copy constructor (can be used to move data from device to host or vice-versa)
101 template <typename other_memory_space>
107
111 _contains_valid_alphas = false; // false until copyAlphas() is called
113
114 // copy from other_memory_space to memory_space (if needed)
115 if (_lro.extent(0) != other._lro.extent(0)) {
116 Kokkos::resize(_lro, other._lro.extent(0));
117 }
118 if (_lro_lookup.extent(0) != other._lro_lookup.extent(0)) {
119 Kokkos::resize(_lro_lookup, other._lro_lookup.extent(0));
120 }
121 if (_lro_total_offsets.extent(0) != other._lro_total_offsets.extent(0)) {
122 Kokkos::resize(_lro_total_offsets, other._lro_total_offsets.extent(0));
123 }
124 if (_lro_output_tile_size.extent(0) != other._lro_output_tile_size.extent(0)) {
125 Kokkos::resize(_lro_output_tile_size, other._lro_output_tile_size.extent(0));
126 }
127 if (_lro_input_tile_size.extent(0) != other._lro_input_tile_size.extent(0)) {
128 Kokkos::resize(_lro_input_tile_size, other._lro_input_tile_size.extent(0));
129 }
130 if (_lro_output_tensor_rank.extent(0) != other._lro_output_tensor_rank.extent(0)) {
131 Kokkos::resize(_lro_output_tensor_rank, other._lro_output_tensor_rank.extent(0));
132 }
133 if (_lro_input_tensor_rank.extent(0) != other._lro_input_tensor_rank.extent(0)) {
134 Kokkos::resize(_lro_input_tensor_rank, other._lro_input_tensor_rank.extent(0));
135 }
136 Kokkos::deep_copy(_lro, other._lro);
137 Kokkos::deep_copy(_lro_lookup, other._lro_lookup);
138 Kokkos::deep_copy(_lro_total_offsets, other._lro_total_offsets);
139 Kokkos::deep_copy(_lro_output_tile_size, other._lro_output_tile_size);
140 Kokkos::deep_copy(_lro_input_tile_size, other._lro_input_tile_size);
141 Kokkos::deep_copy(_lro_output_tensor_rank, other._lro_output_tensor_rank);
142 Kokkos::deep_copy(_lro_input_tensor_rank, other._lro_input_tensor_rank);
143
144 // don't copy _alphas (expensive)
145 // _alphas only copied using copyAlphas
146 }
147
148///@}
149
150/** @name Public Accessors
151 */
152///@{
153
154 // ON DEVICE
155
156 //! Handles offset from operation input/output + extra evaluation sites
157 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
158 KOKKOS_INLINE_FUNCTION
159 int getTargetOffsetIndex(const int lro_num, const int input_component, const int output_component, const int evaluation_site_local_index = 0) const {
160 return ( _total_alpha_values*evaluation_site_local_index
161 + _lro_total_offsets[lro_num]
162 + input_component*_lro_output_tile_size[lro_num]
163 + output_component );
164 }
165
166 //! Helper function for getting alphas for scalar reconstruction from scalar data
167 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
168 KOKKOS_INLINE_FUNCTION
169 double getAlpha0TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int evaluation_site_local_index = 0) const {
170 // e.g. Dirac Delta target of a scalar field
171 return getAlpha(lro, target_index, 0, 0, neighbor_index, 0, 0, evaluation_site_local_index);
172 }
173
174 //! Helper function for getting alphas for vector reconstruction from scalar data
175 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
176 KOKKOS_INLINE_FUNCTION
177 double getAlpha0TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int evaluation_site_local_index = 0) const {
178 // e.g. gradient of a scalar field
179 return getAlpha(lro, target_index, output_component, 0, neighbor_index, 0, 0, evaluation_site_local_index);
180 }
181
182 //! Helper function for getting alphas for matrix reconstruction from scalar data
183 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
184 KOKKOS_INLINE_FUNCTION
185 double getAlpha0TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int evaluation_site_local_index = 0) const {
186 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, 0, 0, evaluation_site_local_index);
187 }
188
189 //! Helper function for getting alphas for scalar reconstruction from vector data
190 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
191 KOKKOS_INLINE_FUNCTION
192 double getAlpha1TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
193 // e.g. divergence of a vector field
194 return getAlpha(lro, target_index, 0, 0, neighbor_index, input_component, 0, evaluation_site_local_index);
195 }
196
197 //! Helper function for getting alphas for vector reconstruction from vector data
198 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
199 KOKKOS_INLINE_FUNCTION
200 double getAlpha1TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
201 // e.g. curl of a vector field
202 return getAlpha(lro, target_index, output_component, 0, neighbor_index, input_component, 0, evaluation_site_local_index);
203 }
204
205 //! Helper function for getting alphas for matrix reconstruction from vector data
206 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
207 KOKKOS_INLINE_FUNCTION
208 double getAlpha1TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
209 // e.g. gradient of a vector field
210 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, input_component, 0, evaluation_site_local_index);
211 }
212
213 //! Helper function for getting alphas for scalar reconstruction from matrix data
214 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
215 KOKKOS_INLINE_FUNCTION
216 double getAlpha2TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
217 return getAlpha(lro, target_index, 0, 0, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
218 }
219
220 //! Helper function for getting alphas for vector reconstruction from matrix data
221 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
222 KOKKOS_INLINE_FUNCTION
223 double getAlpha2TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
224 return getAlpha(lro, target_index, output_component, 0, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
225 }
226
227 //! Helper function for getting alphas for matrix reconstruction from matrix data
228 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
229 KOKKOS_INLINE_FUNCTION
230 double getAlpha2TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
231 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
232 }
233
234 //! Gives index into alphas given two axes, which when incremented by the neighbor number transforms access into
235 //! alphas from a rank 1 view into a rank 3 view.
236 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
237 KOKKOS_INLINE_FUNCTION
238 global_index_type getAlphaIndex(const int target_index, const int alpha_column_offset) const {
239
240 global_index_type total_neighbors_before_target = _neighbor_lists.getRowOffsetDevice(target_index);
241 int total_added_alphas_before_target = target_index*_added_alpha_size;
242
243 int alphas_per_tile_per_target = _neighbor_lists.getNumberOfNeighborsDevice(target_index) + _added_alpha_size;
244
245 return (total_neighbors_before_target+TO_GLOBAL(total_added_alphas_before_target))
247 + TO_GLOBAL(alpha_column_offset*alphas_per_tile_per_target);
248
249 }
250
251 //! Retrieves the offset for an operator based on input and output component, generic to row
252 //! (but still multiplied by the number of neighbors for each row and then needs a neighbor number added
253 //! to this returned value to be meaningful)
254 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
255 KOKKOS_INLINE_FUNCTION
256 int getAlphaColumnOffset(TargetOperation lro, const int output_component_axis_1,
257 const int output_component_axis_2, const int input_component_axis_1,
258 const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
259
260 const int lro_number = _lro_lookup[(int)lro];
261 compadre_kernel_assert_debug((lro_number >= 0) && "getAlphaColumnOffset called for a TargetOperation that was not registered.");
262
263 // the target functional input indexing is sized based on the output rank of the sampling
264 // functional used, which can not be inferred unless a specification of target functional,
265 // reconstruction space, and sampling functional are all known (as was the case at the
266 // construction of this class)
267 const int input_index = getSamplingOutputIndex(_data_sampling_functional, input_component_axis_1, input_component_axis_2);
268 const int output_index = getTargetOutputIndex((int)lro, output_component_axis_1, output_component_axis_2, _dimensions);
269
270 return getTargetOffsetIndex(lro_number, input_index, output_index, evaluation_site_local_index);
271 }
272
273 //! Underlying function all interface helper functions call to retrieve alpha values
274 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
275 KOKKOS_INLINE_FUNCTION
276 double getAlpha(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
277 // lro - the operator from TargetOperations
278 // target_index - the # for the target site where information is required
279 // neighbor_index - the # for the neighbor of the target
280 //
281 // This code support up to rank 2 tensors for inputs and outputs
282 //
283 // scalar reconstruction from scalar data: rank 0 to rank 0
284 // provides 1 piece of information for each neighbor
285 // scalar reconstruction from vector data (e.g. divergence): rank 1 to rank 0
286 // provides 'd' pieces of information for each neighbor
287 // vector reconstruction from scalar data (e.g. gradient): rank 0 to rank 1
288 // provides 'd' piece of information for each neighbor
289 // vector reconstruction from vector data (e.g. curl): rank 1 to rank 1
290 // provides 'd'x'd' pieces of information for each neighbor
291 //
292 // This function would more reasonably be called from one of the getAlphaNTensorFromNTensor
293 // which is much easier to understand with respect to indexing and only requesting indices
294 // that are relavent to the operator in question.
295 //
296
297 compadre_kernel_assert_debug(this->_contains_valid_alphas &&
298 "getAlpha called on SolutionSet with _contains_valid_alphas=false");
299
300 const int alpha_column_offset = this->getAlphaColumnOffset( lro, output_component_axis_1,
301 output_component_axis_2, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
302
303 auto alphas_index = this->getAlphaIndex(target_index, alpha_column_offset);
304 return _alphas(alphas_index + neighbor_index);
305 }
306
307 //! Get the local index (internal) to GMLS for a particular TargetOperation
308 //! Every TargetOperation has a global index which can be readily found in Compadre::TargetOperation
309 //! but this function returns the index used inside of the GMLS class
310 template<typename ms=memory_space, enable_if_t<!std::is_same<host_memory_space, ms>::value, int> = 0>
311 KOKKOS_INLINE_FUNCTION
313 return _lro_lookup[(int)lro];
314 }
315
316 //! Handles offset from operation input/output + extra evaluation sites
317 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
318 int getTargetOffsetIndex(const int lro_num, const int input_component, const int output_component, const int evaluation_site_local_index = 0) const {
319 return ( _total_alpha_values*evaluation_site_local_index
320 + _lro_total_offsets[lro_num]
321 + input_component*_lro_output_tile_size[lro_num]
322 + output_component );
323 }
324
325 //! Helper function for getting alphas for scalar reconstruction from scalar data
326 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
327 double getAlpha0TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int evaluation_site_local_index = 0) const {
328 // e.g. Dirac Delta target of a scalar field
329 return getAlpha(lro, target_index, 0, 0, neighbor_index, 0, 0, evaluation_site_local_index);
330 }
331
332 //! Helper function for getting alphas for vector reconstruction from scalar data
333 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
334 double getAlpha0TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int evaluation_site_local_index = 0) const {
335 // e.g. gradient of a scalar field
336 return getAlpha(lro, target_index, output_component, 0, neighbor_index, 0, 0, evaluation_site_local_index);
337 }
338
339 //! Helper function for getting alphas for matrix reconstruction from scalar data
340 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
341 double getAlpha0TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int evaluation_site_local_index = 0) const {
342 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, 0, 0, evaluation_site_local_index);
343 }
344
345 //! Helper function for getting alphas for scalar reconstruction from vector data
346 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
347 double getAlpha1TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
348 // e.g. divergence of a vector field
349 return getAlpha(lro, target_index, 0, 0, neighbor_index, input_component, 0, evaluation_site_local_index);
350 }
351
352 //! Helper function for getting alphas for vector reconstruction from vector data
353 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
354 double getAlpha1TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
355 // e.g. curl of a vector field
356 return getAlpha(lro, target_index, output_component, 0, neighbor_index, input_component, 0, evaluation_site_local_index);
357 }
358
359 //! Helper function for getting alphas for matrix reconstruction from vector data
360 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
361 double getAlpha1TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component, const int evaluation_site_local_index = 0) const {
362 // e.g. gradient of a vector field
363 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, input_component, 0, evaluation_site_local_index);
364 }
365
366 //! Helper function for getting alphas for scalar reconstruction from matrix data
367 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
368 double getAlpha2TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
369 return getAlpha(lro, target_index, 0, 0, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
370 }
371
372 //! Helper function for getting alphas for vector reconstruction from matrix data
373 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
374 double getAlpha2TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
375 return getAlpha(lro, target_index, output_component, 0, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
376 }
377
378 //! Helper function for getting alphas for matrix reconstruction from matrix data
379 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
380 double getAlpha2TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
381 return getAlpha(lro, target_index, output_component_axis_1, output_component_axis_2, neighbor_index, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
382 }
383
384 //! Gives index into alphas given two axes, which when incremented by the neighbor number transforms access into
385 //! alphas from a rank 1 view into a rank 3 view.
386 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
387 global_index_type getAlphaIndex(const int target_index, const int alpha_column_offset) const {
388
389 global_index_type total_neighbors_before_target = _neighbor_lists.getRowOffsetHost(target_index);
390 int total_added_alphas_before_target = target_index*_added_alpha_size;
391
392 int alphas_per_tile_per_target = _neighbor_lists.getNumberOfNeighborsHost(target_index) + _added_alpha_size;
393
394 return (total_neighbors_before_target+TO_GLOBAL(total_added_alphas_before_target))
396 + TO_GLOBAL(alpha_column_offset*alphas_per_tile_per_target);
397
398 }
399
400 //! Retrieves the offset for an operator based on input and output component, generic to row
401 //! (but still multiplied by the number of neighbors for each row and then needs a neighbor number added
402 //! to this returned value to be meaningful)
403 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
404 int getAlphaColumnOffset(TargetOperation lro, const int output_component_axis_1,
405 const int output_component_axis_2, const int input_component_axis_1,
406 const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
407
408 const int lro_number = _lro_lookup[(int)lro];
409 compadre_kernel_assert_debug((lro_number >= 0) && "getAlphaColumnOffset called for a TargetOperation that was not registered.");
410
411 // the target functional input indexing is sized based on the output rank of the sampling
412 // functional used, which can not be inferred unless a specification of target functional,
413 // reconstruction space, and sampling functional are all known (as was the case at the
414 // construction of this class)
415 const int input_index = getSamplingOutputIndex(_data_sampling_functional, input_component_axis_1, input_component_axis_2);
416 const int output_index = getTargetOutputIndex((int)lro, output_component_axis_1, output_component_axis_2, _dimensions);
417
418 return getTargetOffsetIndex(lro_number, input_index, output_index, evaluation_site_local_index);
419 }
420
421 //! Underlying function all interface helper functions call to retrieve alpha values
422 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
423 double getAlpha(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index = 0) const {
424 // lro - the operator from TargetOperations
425 // target_index - the # for the target site where information is required
426 // neighbor_index - the # for the neighbor of the target
427 //
428 // This code support up to rank 2 tensors for inputs and outputs
429 //
430 // scalar reconstruction from scalar data: rank 0 to rank 0
431 // provides 1 piece of information for each neighbor
432 // scalar reconstruction from vector data (e.g. divergence): rank 1 to rank 0
433 // provides 'd' pieces of information for each neighbor
434 // vector reconstruction from scalar data (e.g. gradient): rank 0 to rank 1
435 // provides 'd' piece of information for each neighbor
436 // vector reconstruction from vector data (e.g. curl): rank 1 to rank 1
437 // provides 'd'x'd' pieces of information for each neighbor
438 //
439 // This function would more reasonably be called from one of the getAlphaNTensorFromNTensor
440 // which is much easier to understand with respect to indexing and only requesting indices
441 // that are relavent to the operator in question.
442 //
443
444 compadre_assert_debug(this->_contains_valid_alphas &&
445 "getAlpha called on SolutionSet with _contains_valid_alphas=false");
446
447 const int alpha_column_offset = this->getAlphaColumnOffset( lro, output_component_axis_1,
448 output_component_axis_2, input_component_axis_1, input_component_axis_2, evaluation_site_local_index);
449
450 auto alphas_index = this->getAlphaIndex(target_index, alpha_column_offset);
451 return _alphas(alphas_index + neighbor_index);
452 }
453
454 //! Get the local index (internal) to GMLS for a particular TargetOperation
455 //! Every TargetOperation has a global index which can be readily found in Compadre::TargetOperation
456 //! but this function returns the index used inside of the GMLS class
457 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
459 return _lro_lookup[(int)lro];
460 }
461
462
463///@}
464
465/** @name Public Modifiers (can only call from host)
466 */
467///@{
468
469 //! Copies alphas between two instances of SolutionSet
470 //! Copying of alphas is intentionally omitted in copy constructor
471 template <typename other_memory_space>
473 if ((void*)this != (void*)&other) {
474 if (_alphas.extent(0) != other._alphas.extent(0)) {
475 Kokkos::resize(_alphas, other._alphas.extent(0));
476 }
477 Kokkos::deep_copy(_alphas, other._alphas);
478 this->_contains_valid_alphas = other._contains_valid_alphas;
479 }
480 }
481
482
483 //! Empties the vector of target functionals to apply to the reconstruction
484 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
486 _lro = decltype(_lro)();
487 for (int i=0; i<TargetOperation::COUNT; ++i) {
488 _lro_lookup[i] = -1;
489 }
490 }
491
492 //! Adds a target to the vector of target functional to be applied to the reconstruction
493 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
495 std::vector<TargetOperation> temporary_lro_vector(1, lro);
496 this->addTargets(temporary_lro_vector);
497 }
498
499 //! Adds a vector of target functionals to the vector of target functionals already to be applied to the reconstruction
500 template<typename ms=memory_space, enable_if_t<std::is_same<host_memory_space, ms>::value, int> = 0>
501 void addTargets(std::vector<TargetOperation> lro) {
502
503 std::vector<TargetOperation> unique_new_lro;
504
505 auto host_lro_lookup = create_mirror_view(_lro_lookup);
506 if (_lro_lookup.extent(0) == 0) {
507 _lro_lookup = decltype(_lro_lookup)("LRO Lookup", TargetOperation::COUNT);
508 host_lro_lookup = create_mirror_view(_lro_lookup);
509 Kokkos::deep_copy(host_lro_lookup, -1);
510 } else {
511 Kokkos::deep_copy(host_lro_lookup, _lro_lookup);
512 }
513
514 // loop over requested targets
515 for (size_t i=0; i<lro.size(); ++i) {
516
517 bool operation_found = false;
518 // loop over existing targets registered
519 for (size_t j=0; j<_lro.size(); ++j) {
520
521 // if found
522 if (_lro(j)==lro[i]) {
523
524 operation_found = true;
525
526 // the operation should now point to where the operation is stored
527 host_lro_lookup[(int)lro[i]] = j;
528
529 break;
530
531 }
532 }
533
534 if (!operation_found) {
535 host_lro_lookup[(int)lro[i]] = _lro.size() + unique_new_lro.size();
536 unique_new_lro.push_back(lro[i]);
537 }
538 }
539
540 // move unique_new_lro into _lro
541 auto new_lro = decltype(_lro)("LRO", _lro.size() + unique_new_lro.size());
542 for (size_t i=0; i<_lro.size(); ++i) {
543 new_lro(i) = _lro(i);
544 }
545 for (size_t i=0; i<unique_new_lro.size(); ++i) {
546 new_lro(i+_lro.size()) = unique_new_lro[i];
547 }
548 _lro = new_lro;
549
550 _lro_total_offsets = decltype(_lro_total_offsets)("total offsets for alphas", _lro.size());
551 _lro_output_tile_size = decltype(_lro_output_tile_size)("output tile size for each operation", _lro.size());
552 _lro_input_tile_size = decltype(_lro_input_tile_size)("output tile size for each operation", _lro.size());
553 _lro_output_tensor_rank = decltype(_lro_output_tensor_rank)("output tensor rank", _lro.size());
554 _lro_input_tensor_rank = decltype(_lro_input_tensor_rank)("input tensor rank", _lro.size());
555
556 auto host_lro_total_offsets = create_mirror_view(_lro_total_offsets);
557 auto host_lro_output_tile_size = create_mirror_view(_lro_output_tile_size);
558 auto host_lro_input_tile_size = create_mirror_view(_lro_input_tile_size);
559 auto host_lro_output_tensor_rank = create_mirror_view(_lro_output_tensor_rank);
560 auto host_lro_input_tensor_rank = create_mirror_view(_lro_input_tensor_rank);
561
562 int total_offset = 0; // need total offset
563
564 for (size_t i=0; i<_lro.size(); ++i) {
565 host_lro_total_offsets(i) = total_offset;
566
567 // allows for a tile of the product of dimension^input_tensor_rank * dimension^output_tensor_rank * the number of neighbors
568 int output_tile_size = getOutputDimensionOfOperation(_lro(i), _local_dimensions);
569
570 // the target functional input indexing is sized based on the output rank of the sampling
571 // functional used
573 host_lro_output_tile_size(i) = output_tile_size;
574 host_lro_input_tile_size(i) = input_tile_size;
575
576 total_offset += input_tile_size * output_tile_size;
577
578 // the target functional output rank is based on the output rank of the sampling
579 // functional used
580 host_lro_input_tensor_rank(i) = _data_sampling_functional.output_rank;
581 host_lro_output_tensor_rank(i) = getTargetOutputTensorRank((int)_lro(i));
582 }
583
584 _total_alpha_values = total_offset;
585
587 // if on a manifold, the total alphas values must be large enough to hold the gradient
588 // of the geometry reconstruction
591 }
592
593 Kokkos::deep_copy(_lro_lookup, host_lro_lookup);
594 Kokkos::deep_copy(_lro_total_offsets, host_lro_total_offsets);
595 Kokkos::deep_copy(_lro_output_tile_size, host_lro_output_tile_size);
596 Kokkos::deep_copy(_lro_input_tile_size, host_lro_input_tile_size);
597 Kokkos::deep_copy(_lro_output_tensor_rank, host_lro_output_tensor_rank);
598 Kokkos::deep_copy(_lro_input_tensor_rank, host_lro_input_tensor_rank);
599 }
600
601 //! Get a view (device) of all alphas
602 decltype(_alphas) getAlphas() const {
603 compadre_assert_debug(this->_contains_valid_alphas &&
604 "getAlpha called on SolutionSet with _contains_valid_alphas=false");
605 return _alphas;
606 }
607
608///@}
609
610}; // SolutionSet
611
612} // Compadre namespace
613
614#endif
615
#define compadre_kernel_assert_debug(condition)
#define compadre_assert_debug(condition)
compadre_assert_debug is used for assertions that are checked in loops, as these significantly impact...
#define TO_GLOBAL(variable)
KOKKOS_INLINE_FUNCTION int pown(int n, unsigned p)
n^p (n^0 returns 1, regardless of n)
KOKKOS_INLINE_FUNCTION int getTargetOutputTensorRank(const int &index)
Rank of target functional output for each TargetOperation Rank of target functional input for each Ta...
constexpr SamplingFunctional PointSample
Available sampling functionals.
ProblemType
Problem type, that optionally can handle manifolds.
@ MANIFOLD
Solve GMLS problem on a manifold (will use QR or SVD to solve the resultant GMLS problem dependent on...
KOKKOS_INLINE_FUNCTION int getOutputDimensionOfOperation(TargetOperation lro, const int local_dimensions)
Dimensions ^ output rank for target operation.
KOKKOS_INLINE_FUNCTION int getTargetOutputIndex(const int operation_num, const int output_component_axis_1, const int output_component_axis_2, const int dimensions)
Helper function for finding alpha coefficients.
TargetOperation
Available target functionals.
@ COUNT
Should be the total count of all available target functionals.
std::size_t global_index_type
KOKKOS_INLINE_FUNCTION int getOutputDimensionOfSampling(SamplingFunctional sro, const int local_dimensions)
Dimensions ^ output rank for sampling operation (always in local chart if on a manifold,...
KOKKOS_INLINE_FUNCTION int getSamplingOutputIndex(const SamplingFunctional sf, const int output_component_axis_1, const int output_component_axis_2)
Helper function for finding alpha coefficients.
NeighborLists assists in accessing entries of compressed row neighborhood lists.
global_index_type getRowOffsetHost(int target_index) const
Get offset into compressed row neighbor lists (host)
KOKKOS_INLINE_FUNCTION global_index_type getRowOffsetDevice(int target_index) const
Get offset into compressed row neighbor lists (device)
KOKKOS_INLINE_FUNCTION int getNumberOfNeighborsDevice(int target_index) const
Get number of neighbors for a given target (device)
int getNumberOfNeighborsHost(int target_index) const
Get number of neighbors for a given target (host)
int output_rank
Rank of sampling functional output for each SamplingFunctional.
All vairables and functionality related to the layout and storage of GMLS solutions (alpha values)
KOKKOS_INLINE_FUNCTION double getAlpha0TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from scalar data.
KOKKOS_INLINE_FUNCTION double getAlpha0TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from scalar data.
KOKKOS_INLINE_FUNCTION double getAlpha2TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from matrix data.
KOKKOS_INLINE_FUNCTION double getAlpha0TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from scalar data.
void addTargets(TargetOperation lro)
Adds a target to the vector of target functional to be applied to the reconstruction.
Kokkos::View< int *, memory_space > _lro_output_tile_size
dimensions ^ rank of tensor of output for each target functional
KOKKOS_INLINE_FUNCTION double getAlpha1TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from vector data.
KOKKOS_INLINE_FUNCTION global_index_type getAlphaIndex(const int target_index, const int alpha_column_offset) const
Gives index into alphas given two axes, which when incremented by the neighbor number transforms acce...
double getAlpha2TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from matrix data.
global_index_type getAlphaIndex(const int target_index, const int alpha_column_offset) const
Gives index into alphas given two axes, which when incremented by the neighbor number transforms acce...
KOKKOS_INLINE_FUNCTION double getAlpha2TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from matrix data.
SolutionSet(SamplingFunctional data_sampling_functional, int dimensions, int local_dimensions, const ProblemType problem_type)
Constructor for SolutionSet.
Kokkos::View< int *, memory_space > _lro_input_tensor_rank
tensor rank of sampling functional (device)
void clearTargets()
Empties the vector of target functionals to apply to the reconstruction.
double getAlpha0TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from scalar data.
int getTargetOffsetIndex(const int lro_num, const int input_component, const int output_component, const int evaluation_site_local_index=0) const
Handles offset from operation input/output + extra evaluation sites.
Kokkos::View< int *, memory_space > _lro_input_tile_size
dimensions ^ rank of tensor of output for each sampling functional
KOKKOS_INLINE_FUNCTION double getAlpha2TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from matrix data.
KOKKOS_INLINE_FUNCTION int getTargetOperationLocalIndex(TargetOperation lro) const
Get the local index (internal) to GMLS for a particular TargetOperation Every TargetOperation has a g...
Kokkos::View< TargetOperation *, memory_space > _lro
vector of user requested target operations
double getAlpha0TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from scalar data.
int _dimensions
dimension of the problem, set at class instantiation only
int getTargetOperationLocalIndex(TargetOperation lro) const
Get the local index (internal) to GMLS for a particular TargetOperation Every TargetOperation has a g...
NeighborLists< Kokkos::View< int * > > _neighbor_lists
Accessor to get neighbor list data, offset data, and number of neighbors per target.
int _max_evaluation_sites_per_target
maximum number of evaluation sites for each target (includes target site)
SamplingFunctional _data_sampling_functional
generally the same as _polynomial_sampling_functional, but can differ if specified at GMLS class inst...
Kokkos::View< double *, layout_right, memory_space > _alphas
generated alpha coefficients (device)
int _added_alpha_size
additional alpha coefficients due to constraints
KOKKOS_INLINE_FUNCTION int getAlphaColumnOffset(TargetOperation lro, const int output_component_axis_1, const int output_component_axis_2, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Retrieves the offset for an operator based on input and output component, generic to row (but still m...
Kokkos::View< int *, memory_space > _lro_output_tensor_rank
tensor rank of target functional (device)
double getAlpha(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Underlying function all interface helper functions call to retrieve alpha values.
double getAlpha2TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from matrix data.
decltype(_alphas) getAlphas() const
Get a view (device) of all alphas.
bool _contains_valid_alphas
whether internal alpha values are valid (set externally on a solve)
double getAlpha0TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from scalar data.
Kokkos::View< int *, memory_space > _lro_lookup
vector containing a mapping from a target functionals enum value to the its place in the list of targ...
void addTargets(std::vector< TargetOperation > lro)
Adds a vector of target functionals to the vector of target functionals already to be applied to the ...
double getAlpha1TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from vector data.
double getAlpha1TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from vector data.
double getAlpha2TensorTo1Tensor(TargetOperation lro, const int target_index, const int output_component, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Helper function for getting alphas for vector reconstruction from matrix data.
void copyAlphas(SolutionSet< other_memory_space > &other)
Copies alphas between two instances of SolutionSet Copying of alphas is intentionally omitted in copy...
KOKKOS_INLINE_FUNCTION double getAlpha1TensorTo2Tensor(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for matrix reconstruction from vector data.
Kokkos::View< int *, memory_space > _lro_total_offsets
index for where this operation begins the for _alpha coefficients
int _total_alpha_values
used for sizing P_target_row and the _alphas view
ProblemType _problem_type
problem type for GMLS problem, can also be set to STANDARD for normal or MANIFOLD for manifold proble...
KOKKOS_INLINE_FUNCTION double getAlpha1TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from vector data.
KOKKOS_INLINE_FUNCTION int getTargetOffsetIndex(const int lro_num, const int input_component, const int output_component, const int evaluation_site_local_index=0) const
Handles offset from operation input/output + extra evaluation sites.
int getAlphaColumnOffset(TargetOperation lro, const int output_component_axis_1, const int output_component_axis_2, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Retrieves the offset for an operator based on input and output component, generic to row (but still m...
SolutionSet(const SolutionSet< other_memory_space > &other)
Copy constructor (can be used to move data from device to host or vice-versa)
int _local_dimensions
dimension of the problem, set at class instantiation only. For manifolds, generally _global_dimension...
double getAlpha1TensorTo0Tensor(TargetOperation lro, const int target_index, const int neighbor_index, const int input_component, const int evaluation_site_local_index=0) const
Helper function for getting alphas for scalar reconstruction from vector data.
KOKKOS_INLINE_FUNCTION double getAlpha(TargetOperation lro, const int target_index, const int output_component_axis_1, const int output_component_axis_2, const int neighbor_index, const int input_component_axis_1, const int input_component_axis_2, const int evaluation_site_local_index=0) const
Underlying function all interface helper functions call to retrieve alpha values.