ProductMapsTimeDep.hpp
1 // Distributed under the MIT License.
2 // See LICENSE.txt for details.
3 
4 #pragma once
5 
6 #include <array>
7 #include <boost/optional.hpp>
8 #include <cstddef>
9 #include <functional>
10 #include <limits>
11 #include <string>
12 #include <unordered_map>
13 #include <utility>
14 
16 #include "Domain/CoordinateMaps/TimeDependentHelpers.hpp"
17 #include "Domain/FunctionsOfTime/FunctionOfTime.hpp"
20 #include "Utilities/TMPL.hpp"
21 #include "Utilities/TypeTraits.hpp"
22 
23 /// \cond
24 namespace PUP {
25 class er;
26 } // namespace PUP
27 /// \endcond
28 
29 namespace domain {
30 namespace CoordMapsTimeDependent {
31 /// \ingroup CoordMapsTimeDependentGroup
32 /// \brief Product of two codimension=0 CoordinateMaps, where one or both must
33 /// be time-dependent.
34 ///
35 /// \tparam Map1 the map for the first coordinate(s)
36 /// \tparam Map2 the map for the second coordinate(s)
37 template <typename Map1, typename Map2>
39  public:
40  static constexpr size_t dim = Map1::dim + Map2::dim;
41  using map_list = tmpl::list<Map1, Map2>;
42  static_assert(dim == 2 or dim == 3,
43  "Only 2D and 3D maps are supported by ProductOf2Maps");
44  static_assert(
45  domain::is_map_time_dependent_v<Map1> or
46  domain::is_map_time_dependent_v<Map2>,
47  "Either Map1 or Map2 must be time-dependent for time-dependent product "
48  "maps. A time-independent product map exists in domain::CoordinateMaps.");
49 
50  // Needed for Charm++ serialization
51  ProductOf2Maps() = default;
52 
53  ProductOf2Maps(Map1 map1, Map2 map2) noexcept;
54 
55  template <typename T>
57  const std::array<T, dim>& source_coords, double time,
58  const std::unordered_map<
61  functions_of_time) const noexcept;
62 
63  boost::optional<std::array<double, dim>> inverse(
64  const std::array<double, dim>& target_coords, double time,
65  const std::unordered_map<
68  functions_of_time) const noexcept;
69 
70  template <typename T>
71  std::array<tt::remove_cvref_wrap_t<T>, dim> frame_velocity(
72  const std::array<T, dim>& source_coords, double time,
73  const std::unordered_map<
76  functions_of_time) const noexcept;
77 
78  template <typename T>
79  tnsr::Ij<tt::remove_cvref_wrap_t<T>, dim, Frame::NoFrame> inv_jacobian(
80  const std::array<T, dim>& source_coords, double time,
81  const std::unordered_map<
84  functions_of_time) const noexcept;
85 
86  template <typename T>
87  tnsr::Ij<tt::remove_cvref_wrap_t<T>, dim, Frame::NoFrame> jacobian(
88  const std::array<T, dim>& source_coords, double time,
89  const std::unordered_map<
92  functions_of_time) const noexcept;
93 
94  // clang-tidy: google-runtime-references
95  void pup(PUP::er& p); // NOLINT
96 
97  bool is_identity() const noexcept {
98  return map1_.is_identity() and map2_.is_identity();
99  }
100 
101  private:
102  friend bool operator==(const ProductOf2Maps& lhs,
103  const ProductOf2Maps& rhs) noexcept {
104  return lhs.map1_ == rhs.map1_ and lhs.map2_ == rhs.map2_;
105  }
106 
107  Map1 map1_;
108  Map2 map2_;
109 };
110 
111 template <typename Map1, typename Map2>
112 bool operator!=(const ProductOf2Maps<Map1, Map2>& lhs,
113  const ProductOf2Maps<Map1, Map2>& rhs) noexcept;
114 
115 /// \ingroup CoordinateMapsGroup
116 /// \brief Product of three one-dimensional CoordinateMaps.
117 template <typename Map1, typename Map2, typename Map3>
119  public:
120  static constexpr size_t dim = Map1::dim + Map2::dim + Map3::dim;
121  using map_list = tmpl::list<Map1, Map2, Map3>;
122  static_assert(dim == 3, "Only 3D maps are implemented for ProductOf3Maps");
123  static_assert(
124  domain::is_map_time_dependent_v<Map1> or
125  domain::is_map_time_dependent_v<Map2> or
126  domain::is_map_time_dependent_v<Map3>,
127  "Either Map1, Map2, or Map3 must be time-dependent for time-dependent "
128  "product maps. A time-independent product map exists in "
129  "domain::CoordinateMaps.");
130 
131  // Needed for Charm++ serialization
132  ProductOf3Maps() = default;
133 
134  ProductOf3Maps(Map1 map1, Map2 map2, Map3 map3) noexcept;
135 
136  template <typename T>
137  std::array<tt::remove_cvref_wrap_t<T>, dim> operator()(
138  const std::array<T, dim>& source_coords, double time,
139  const std::unordered_map<
140  std::string,
142  functions_of_time) const noexcept;
143 
144  boost::optional<std::array<double, dim>> inverse(
145  const std::array<double, dim>& target_coords, double time,
146  const std::unordered_map<
147  std::string,
149  functions_of_time) const noexcept;
150 
151  template <typename T>
152  std::array<tt::remove_cvref_wrap_t<T>, dim> frame_velocity(
153  const std::array<T, dim>& source_coords, double time,
154  const std::unordered_map<
155  std::string,
157  functions_of_time) const noexcept;
158 
159  template <typename T>
160  tnsr::Ij<tt::remove_cvref_wrap_t<T>, dim, Frame::NoFrame> inv_jacobian(
161  const std::array<T, dim>& source_coords, double time,
162  const std::unordered_map<
163  std::string,
165  functions_of_time) const noexcept;
166 
167  template <typename T>
168  tnsr::Ij<tt::remove_cvref_wrap_t<T>, dim, Frame::NoFrame> jacobian(
169  const std::array<T, dim>& source_coords, double time,
170  const std::unordered_map<
171  std::string,
173  functions_of_time) const noexcept;
174 
175  // clang-tidy: google-runtime-references
176  void pup(PUP::er& p) noexcept; // NOLINT
177 
178  bool is_identity() const noexcept {
179  return map1_.is_identity() and map2_.is_identity() and map3_.is_identity();
180  }
181 
182  private:
183  friend bool operator==(const ProductOf3Maps& lhs,
184  const ProductOf3Maps& rhs) noexcept {
185  return lhs.map1_ == rhs.map1_ and lhs.map2_ == rhs.map2_ and
186  lhs.map3_ == rhs.map3_;
187  }
188 
189  Map1 map1_;
190  Map2 map2_;
191  Map3 map3_;
192 };
193 
194 template <typename Map1, typename Map2, typename Map3>
195 bool operator!=(const ProductOf3Maps<Map1, Map2, Map3>& lhs,
196  const ProductOf3Maps<Map1, Map2, Map3>& rhs) noexcept;
197 } // namespace CoordMapsTimeDependent
198 } // namespace domain
Defines function dereference_wrapper.
Definition: Strahlkorper.hpp:14
Definition: BlockId.hpp:16
Product of three one-dimensional CoordinateMaps.
Definition: ProductMapsTimeDep.hpp:118
Defines classes for Tensor.
Represents an index that is not in a known frame, e.g. some internal intermediate frame that is irrel...
Definition: IndexType.hpp:48
Wraps the template metaprogramming library used (brigand)
Defines type traits, some of which are future STL type_traits header.
Product of two codimension=0 CoordinateMaps, where one or both must be time-dependent.
Definition: ProductMapsTimeDep.hpp:38
Defines make_with_value.