Saddle-Point
Loading...
Searching...
No Matches
rhs_function.h
Go to the documentation of this file.
1
14#ifndef rhs_function_h
15#define rhs_function_h
16
17#include <deal.II/base/point.h>
18#include <deal.II/base/function.h>
19#include <deal.II/base/geometric_utilities.h>
20#include <deal.II/base/tensor.h>
21#include <cmath>
22
23using namespace dealii;
24
54template <int dim>
55class RHSFunction : public Function<dim>
56{
57public:
70
78 : Function<dim>(1), function_type(type) {}
79
91 virtual double value(const Point<dim> & p,
92 const unsigned int component = 0) const override;
93
106 virtual Tensor<1, dim> gradient(const Point<dim> & p,
107 const unsigned int component = 0) const override;
108
109private:
111 FunctionType function_type;
112
114 int R = 2;
115};
116
117// Out-of-line implementation of RHSFunction::value() (see class
118// description for documentation). Dispatch is done with a chain of
119// `if/else if` branches; the default branch returns 0.
120template <int dim>
121double RHSFunction<dim>::value(const Point<dim> &p, const unsigned int /*comp*/) const
122{
123 double return_value;
124 if (function_type == TYPE_ZERO) {
125 return 0;
126 }
127 else if (function_type == TYPE_SIN_SIN) {
128 // Alternative right-hand side scaled with pi (commented out):
129 //double pi = M_PI;
130 //return 2 * pi * pi * std::sin(pi * p[0]) * std::sin(pi * p[1]);
131 return 2 * std::sin(p[0]) * std::sin(p[1]);
132 }
133 else if (function_type == TYPE_X_Y) {
134 return -10 * p[0] * p[1];
135 }
136 else if (function_type == TYPE_R_COS) {
137 const auto r = p.norm();
138 const auto theta = std::atan(p[1]/p[0]);
139 return (r - 1/r - (1/r)*(1/R)*(1/R)) * std::cos(theta/R);
140 }
141 return_value = 0;
142 return return_value;
143}
144
145
146// Out-of-line implementation of RHSFunction::gradient() (see class
147// description for documentation). Returns the analytic gradient of the
148// function selected by FunctionType; the TYPE_R_COS branch is an
149// alternative test case using polar coordinates that we did not end up
150// using for the final manufactured solution but is retained for reference.
151template <int dim>
152Tensor<1, dim> RHSFunction<dim>::gradient(const Point<dim> &p,
153 const unsigned int /*comp*/) const
154{
155 Tensor<1, dim> return_values;
156 return_values = 0;
157 if (function_type == TYPE_ZERO) {
158 return_values[0] = 0;
159 return_values[1] = 0;
160 }
161 else if (function_type == TYPE_X_Y) {
162 return_values[0] = -10 * p[1];
163 return_values[1] = -10 * p[0];
164 }
165 else if (function_type == TYPE_SIN_SIN) {
166 double pi = M_PI;
167 return_values[0] = 2 * pi * pi * pi * std::cos(pi * p[0]) * std::sin(pi * p[1]);
168 return_values[1] = 2 * pi * pi * pi * std::sin(pi * p[0]) * std::cos(pi * p[1]);
169 return return_values;
170 }
171 else if (function_type == TYPE_R_COS) {
172 // RHS gradient of an alternative test case in polar coordinates.
173 // We ended up using a different test case in the final program.
174 const auto r = p.norm();
175 const auto theta = std::atan(p[1]/p[0]);
176 return_values[0] = (1 + (1/r)*(1/r)*(1 + (1/R)*(1/R))) * std::cos(theta/R);
177 return_values[1] = (r - 1/r - (1/r) * (1/R) * (1/R)) * (-1) * std::sin(theta/R);
178 }
179 return return_values;
180}
181
182
183//template class RHSFunction<2>;
184//template class RHSFunction<3>;
185
186#endif
Analytic right-hand-side function for the saddle-point Laplace problem.
Definition rhs_function.h:56
RHSFunction(FunctionType type)
Construct a single-component RHSFunction of the requested type.
Definition rhs_function.h:77
virtual Tensor< 1, dim > gradient(const Point< dim > &p, const unsigned int component=0) const override
Evaluate the analytic gradient at point p.
Definition rhs_function.h:152
FunctionType
Selector for the analytic right-hand-side expression to use.
Definition rhs_function.h:61
@ TYPE_R_COS
Definition rhs_function.h:67
@ TYPE_X_Y
Definition rhs_function.h:62
@ TYPE_EXP_COS
Definition rhs_function.h:63
@ TYPE_ZERO
Definition rhs_function.h:65
@ TYPE_SIN_SIN
Definition rhs_function.h:66
virtual double value(const Point< dim > &p, const unsigned int component=0) const override
Evaluate the analytic right-hand side at point p.
Definition rhs_function.h:121