Compadre  1.5.9
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
GMLS_Manifold.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 _GMLS_MANIFOLD_HPP_
10 #define _GMLS_MANIFOLD_HPP_
11 
12 #include <Kokkos_Core.hpp>
13 #include <cmath>
14 
15 #define PI 3.14159265358979323846
16 
17 KOKKOS_INLINE_FUNCTION
18 double device_max(double d1, double d2) {
19  return (d1 > d2) ? d1 : d2;
20 }
21 
22 KOKKOS_INLINE_FUNCTION
23 double atan4(const double y, const double x) {
24  double result = 0.0;
25  if (x == 0.0)
26  {
27  if (y > 0.0)
28  result = 0.5 * PI;
29  else if ( y < 0.0 )
30  result = 1.5 * PI;
31  else if ( y == 0.0 )
32  result = 0.0;
33  }
34  else if (y == 0)
35  {
36  if (x > 0.0)
37  result = 0.0;
38  else if ( x < 0.0 )
39  result = PI;
40  }
41  else
42  {
43  double theta = std::atan2( std::abs(y), std::abs(x) );
44  if (x > 0.0 && y > 0.0)
45  result = theta;
46  else if ( x < 0.0 && y > 0.0 )
47  result = PI - theta;
48  else if ( x < 0.0 && y < 0.0 )
49  result = PI + theta;
50  else if ( x > 0.0 && y < 0.0 )
51  result = 2.0 * PI - theta;
52  }
53  return result;
54 }
55 
56 KOKKOS_INLINE_FUNCTION
57 double latitude(double x, double y, double z) {
58  return std::atan2(z, std::sqrt( x*x + y*y));
59 }
60 
61 KOKKOS_INLINE_FUNCTION
62 double longitude(double x, double y, double z) {
63  return atan4(y, x);
64 }
65 
66 KOKKOS_INLINE_FUNCTION
67 double legendre54(double z) {
68  return z * ( z * z - 1.0 ) * ( z * z - 1.0 );
69 }
70 
71 KOKKOS_INLINE_FUNCTION
72 double sphere_harmonic54(double x, double y, double z) {
73  const double lon = longitude(x, y, z);
74  return std::cos(4.0 * lon) * legendre54(z);
75 }
76 
77 KOKKOS_INLINE_FUNCTION
78 void curl_sphere_harmonic54(double *curl, double x, double y, double z) {
79  const scalar_type lon = longitude(x, y, z); // theta
80  const scalar_type lat = acos(z); // phi
81  const scalar_type sigma_lon_comp = std::pow(sin(lat), 2) * (5.0* std::pow(cos(lat), 2) - 1.0) * cos(4.0 *lon);
82  const scalar_type sigma_lat_comp = 4*cos(lat) * std::pow(sin(lat), 3) * sin(4.0 * lon);
83  // solution oriented for inward normal, so we flip sign for outward
84  curl[0] = -(-sin(lat)*sin(lon)*sigma_lon_comp + cos(lat)*cos(lon)*sigma_lat_comp);
85  curl[1] = -(sin(lat)*cos(lon)*sigma_lon_comp + cos(lat)*sin(lon)*sigma_lat_comp);
86  curl[2] = -(-sin(lat)*sigma_lat_comp);
87 }
88 
89 
90 KOKKOS_INLINE_FUNCTION
91 double laplace_beltrami_sphere_harmonic54(double x, double y, double z) {
92  const double lon = longitude(x, y, z);
93  return -30 * std::cos(4.0 * lon) * legendre54(z);
94 }
95 
96 KOKKOS_INLINE_FUNCTION
97 void gradient_sphereHarmonic54_local(double *gradient, double x, double y, double z) {
98  const double lat = latitude(x, y, z); // phi
99  const double lon = longitude(x, y, z); // lambda
100 
101  const double A = -4.0 * std::pow(std::cos(lat),3) * std::sin(4.0 * lon) * std::sin(lat);
102  const double B = 0.5* std::cos(4.0 * lon) * std::pow(std::cos(lat),3) * ( 5 * std::cos(2.0 * lat) - 3.0 );
103 
104  gradient[0] = A;
105  gradient[1] = B;
106 }
107 
108 KOKKOS_INLINE_FUNCTION
109 void gradient_sphereHarmonic54_ambient(double *gradient, double x, double y, double z) {
110  const double lat = latitude(x, y, z); // phi
111  const double lon = longitude(x, y, z); // lambda
112 
113  const double A = -4.0 * std::pow(std::cos(lat),3) * std::sin(4.0 * lon) * std::sin(lat);
114  const double B = 0.5* std::cos(4.0 * lon) * std::pow(std::cos(lat),3) * ( 5 * std::cos(2.0 * lat) - 3.0 );
115 
116  gradient[0] = -A * std::sin(lon) - B * std::sin(lat) * std::cos(lon);
117  gradient[1] = A * std::cos(lon) - B * std::sin(lat) * std::sin(lon);
118  gradient[2] = B * std::cos(lat);
119 }
120 
121 KOKKOS_INLINE_FUNCTION
122 void velocity_sphereHarmonic54_ambient(double *velocity, double x, double y, double z) {
123  const double lat = latitude(x, y, z); // phi
124  const double lon = longitude(x, y, z); // lambda
125 
126  const double U = 0.5* std::cos(4.0 * lon) * std::pow(std::cos(lat),3) * ( 5 * std::cos(2.0 * lat) - 3.0 );
127  const double V = 4.0 * std::pow(std::cos(lat),3) * std::sin(4.0 * lon) * std::sin(lat);
128 
129  velocity[0] = -U * std::sin(lon) - V * std::sin(lat) * std::cos(lon);
130  velocity[1] = U * std::cos(lon) - V * std::sin(lat) * std::sin(lon);
131  velocity[2] = V * std::cos(lat);
132 }
133 
134 
135 
136 /** Manifold GMLS Example
137  *
138  * Exercises GMLS operator evaluation with data over various orders and numbers of targets for targets including point evaluation, Laplace-Beltrami, gradient and gradient on a manifold.
139  */
140 int main (int argc, char* args[]);
141 
142 /**
143  * \example "Manifold GMLS Tutorial" based on GMLS_Manifold.cpp
144  * \section ex GMLS Example with Device Views
145  *
146  * This tutorial sets up a batch of GMLS problems, solves the minimization problems, and applies the coefficients produced to data.
147  *
148  * \section ex1a Parse Command Line Arguments
149  * \snippet GMLS_Manifold.cpp Parse Command Line Arguments
150  *
151  * \section ex1b Setting Up The Point Cloud
152  * \snippet GMLS_Manifold.cpp Setting Up The Point Cloud
153  *
154  * \section ex1c Performing Neighbor Search
155  * \snippet GMLS_Manifold.cpp Performing Neighbor Search
156  *
157  * \section ex2 Creating The Data
158  * \snippet GMLS_Manifold.cpp Creating The Data
159  *
160  * \section ex3 Setting Up The GMLS Object
161  * \snippet GMLS_Manifold.cpp Setting Up The GMLS Object
162  *
163  * \section ex4 Apply GMLS Alphas To Data
164  * \snippet GMLS_Manifold.cpp Apply GMLS Alphas To Data
165  *
166  * \section ex5 Check That Solutions Are Correct
167  * \snippet GMLS_Manifold.cpp Check That Solutions Are Correct
168  *
169  * \section ex6 Finalize Program
170  * \snippet GMLS_Manifold.cpp Finalize Program
171  */
172 
173 #endif
KOKKOS_INLINE_FUNCTION double sphere_harmonic54(double x, double y, double z)
double scalar_type
KOKKOS_INLINE_FUNCTION void gradient_sphereHarmonic54_local(double *gradient, double x, double y, double z)
KOKKOS_INLINE_FUNCTION double latitude(double x, double y, double z)
int main(int argc, char **argv)
#define PI
KOKKOS_INLINE_FUNCTION void curl_sphere_harmonic54(double *curl, double x, double y, double z)
KOKKOS_INLINE_FUNCTION double atan4(const double y, const double x)
KOKKOS_INLINE_FUNCTION double device_max(double d1, double d2)
KOKKOS_INLINE_FUNCTION double longitude(double x, double y, double z)
KOKKOS_INLINE_FUNCTION double legendre54(double z)
KOKKOS_INLINE_FUNCTION void velocity_sphereHarmonic54_ambient(double *velocity, double x, double y, double z)
KOKKOS_INLINE_FUNCTION void gradient_sphereHarmonic54_ambient(double *gradient, double x, double y, double z)
KOKKOS_INLINE_FUNCTION double laplace_beltrami_sphere_harmonic54(double x, double y, double z)