Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <cstddef>
7 : #include <pup.h>
8 :
9 : #include "DataStructures/CachedTempBuffer.hpp"
10 : #include "DataStructures/DataBox/Prefixes.hpp"
11 : #include "DataStructures/DataVector.hpp"
12 : #include "DataStructures/TaggedTuple.hpp"
13 : #include "DataStructures/Tensor/Tensor.hpp"
14 : #include "Elliptic/Systems/Poisson/Tags.hpp"
15 : #include "NumericalAlgorithms/LinearOperators/PartialDerivatives.hpp"
16 : #include "NumericalAlgorithms/Spectral/Mesh.hpp"
17 : #include "Options/String.hpp"
18 : #include "PointwiseFunctions/InitialDataUtilities/AnalyticSolution.hpp"
19 : #include "PointwiseFunctions/MathFunctions/MathFunction.hpp"
20 : #include "Utilities/ContainerHelpers.hpp"
21 : #include "Utilities/Gsl.hpp"
22 : #include "Utilities/TMPL.hpp"
23 :
24 : namespace Poisson::Solutions {
25 :
26 : namespace detail {
27 : template <typename DataType, size_t Dim>
28 : struct MathFunctionVariables {
29 : using Cache = CachedTempBuffer<
30 : Tags::Field<DataType>,
31 : ::Tags::deriv<Tags::Field<DataType>, tmpl::size_t<Dim>, Frame::Inertial>,
32 : ::Tags::Flux<Tags::Field<DataType>, tmpl::size_t<Dim>, Frame::Inertial>,
33 : ::Tags::FixedSource<Tags::Field<DataType>>>;
34 :
35 : const tnsr::I<DataType, Dim>& x;
36 : const ::MathFunction<Dim, Frame::Inertial>& math_function;
37 :
38 : void operator()(gsl::not_null<Scalar<DataType>*> field,
39 : gsl::not_null<Cache*> cache,
40 : Tags::Field<DataType> /*meta*/) const;
41 : void operator()(gsl::not_null<tnsr::i<DataType, Dim>*> field_gradient,
42 : gsl::not_null<Cache*> cache,
43 : ::Tags::deriv<Tags::Field<DataType>, tmpl::size_t<Dim>,
44 : Frame::Inertial> /*meta*/) const;
45 : void operator()(gsl::not_null<tnsr::I<DataType, Dim>*> flux_for_field,
46 : gsl::not_null<Cache*> cache,
47 : ::Tags::Flux<Tags::Field<DataType>, tmpl::size_t<Dim>,
48 : Frame::Inertial> /*meta*/) const;
49 : void operator()(gsl::not_null<Scalar<DataType>*> fixed_source_for_field,
50 : gsl::not_null<Cache*> cache,
51 : ::Tags::FixedSource<Tags::Field<DataType>> /*meta*/) const;
52 : };
53 : } // namespace detail
54 :
55 : template <size_t Dim>
56 0 : class MathFunction : public elliptic::analytic_data::AnalyticSolution {
57 : public:
58 0 : struct Function {
59 0 : using type = std::unique_ptr<::MathFunction<Dim, Frame::Inertial>>;
60 0 : static constexpr Options::String help = "The solution function";
61 : };
62 :
63 0 : using options = tmpl::list<Function>;
64 0 : static constexpr Options::String help{
65 : "Any solution to the Poisson equation given by a MathFunction "
66 : "implementation, such as a Gaussian."};
67 :
68 0 : MathFunction() = default;
69 0 : MathFunction(const MathFunction&) = delete;
70 0 : MathFunction& operator=(const MathFunction&) = delete;
71 0 : MathFunction(MathFunction&&) = default;
72 0 : MathFunction& operator=(MathFunction&&) = default;
73 0 : ~MathFunction() override = default;
74 0 : std::unique_ptr<elliptic::analytic_data::AnalyticSolution> get_clone()
75 : const override;
76 :
77 0 : MathFunction(
78 : std::unique_ptr<::MathFunction<Dim, Frame::Inertial>> math_function);
79 :
80 0 : const ::MathFunction<Dim, Frame::Inertial>& math_function() const {
81 : return *math_function_;
82 : }
83 :
84 : /// \cond
85 : explicit MathFunction(CkMigrateMessage* m);
86 : using PUP::able::register_constructor;
87 : WRAPPED_PUPable_decl_template(MathFunction); // NOLINT
88 : /// \endcond
89 :
90 : template <typename DataType, typename... RequestedTags>
91 0 : tuples::TaggedTuple<RequestedTags...> variables(
92 : const tnsr::I<DataType, Dim>& x,
93 : tmpl::list<RequestedTags...> /*meta*/) const {
94 : using VarsComputer = detail::MathFunctionVariables<DataType, Dim>;
95 : typename VarsComputer::Cache cache{get_size(*x.begin())};
96 : const VarsComputer computer{x, *math_function_};
97 : return {cache.get_var(computer, RequestedTags{})...};
98 : }
99 :
100 : template <typename... RequestedTags>
101 0 : tuples::TaggedTuple<RequestedTags...> variables(
102 : const tnsr::I<DataVector, Dim>& x, const Mesh<Dim>& /*mesh*/,
103 : const InverseJacobian<DataVector, Dim, Frame::ElementLogical,
104 : Frame::Inertial>& /*inv_jacobian*/,
105 : tmpl::list<RequestedTags...> meta) const {
106 : return variables(x, meta);
107 : }
108 :
109 : // NOLINTNEXTLINE(google-runtime-references)
110 0 : void pup(PUP::er& p) override;
111 :
112 : private:
113 0 : std::unique_ptr<::MathFunction<Dim, Frame::Inertial>> math_function_;
114 : };
115 :
116 : template <size_t Dim>
117 0 : bool operator==(const MathFunction<Dim>& lhs, const MathFunction<Dim>& rhs);
118 :
119 : template <size_t Dim>
120 0 : bool operator!=(const MathFunction<Dim>& lhs, const MathFunction<Dim>& rhs);
121 :
122 : } // namespace Poisson::Solutions
|