Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <boost/preprocessor/arithmetic/dec.hpp>
7 : #include <boost/preprocessor/arithmetic/inc.hpp>
8 : #include <boost/preprocessor/control/expr_iif.hpp>
9 : #include <boost/preprocessor/list/adt.hpp>
10 : #include <boost/preprocessor/repetition/for.hpp>
11 : #include <boost/preprocessor/repetition/repeat.hpp>
12 : #include <boost/preprocessor/tuple/to_list.hpp>
13 : #include <cstddef>
14 : #include <limits>
15 : #include <memory>
16 : #include <pup.h>
17 :
18 : #include "DataStructures/Tensor/Tensor.hpp"
19 : #include "DataStructures/Tensor/TypeAliases.hpp"
20 : #include "Options/String.hpp"
21 : #include "PointwiseFunctions/Hydro/EquationsOfState/EquationOfState.hpp"
22 : #include "PointwiseFunctions/Hydro/Units.hpp"
23 : #include "Utilities/Serialization/CharmPupable.hpp"
24 : #include "Utilities/TMPL.hpp"
25 :
26 : namespace EquationsOfState {
27 : /*!
28 : * \ingroup EquationsOfStateGroup
29 : * \brief A 3D equation of state representing a fluid in compositional
30 : * equalibrium.
31 : *
32 : *
33 : * The equation of state takes the form
34 : *
35 : * \f[
36 : * p = p (T, rho, Y_e) = p(T, rho, Y_e= Y_{e, \beta})
37 : * \f]
38 : *
39 : * where \f$\rho\f$ is the rest mass density and \f$T\f$ is the
40 : * temperaturee; \f$Y_e\f$ the electron fraction, is not
41 : * used, and therefore this evaluating this EoS at any arbtirary
42 : * electron fraction is equivalent to evaluating it in beta equalibrium
43 : *
44 : */
45 : template <typename EquilEos>
46 1 : class Equilibrium3D : public EquationOfState<EquilEos::is_relativistic, 3> {
47 : public:
48 0 : static constexpr size_t thermodynamic_dim = 3;
49 0 : static constexpr bool is_relativistic = EquilEos::is_relativistic;
50 0 : static std::string name() {
51 : return "Equilibrium3D(" + pretty_type::name<EquilEos>() + ")";
52 : }
53 0 : static constexpr Options::String help = {
54 : "An 3D EoS which is independent of electron fraction. "
55 : "Contains an underlying 2D EoS which is dependent only "
56 : "on rest mass density and temperature/internal energy."};
57 :
58 0 : struct UnderlyingEos {
59 0 : using type = EquilEos;
60 0 : static std::string name() { return pretty_type::short_name<EquilEos>(); }
61 0 : static constexpr Options::String help{
62 : "The underlying Eos which is being represented as a "
63 : "3D Eos. Must be a 2D EoS"};
64 : };
65 :
66 0 : using options = tmpl::list<UnderlyingEos>;
67 :
68 0 : Equilibrium3D() = default;
69 0 : Equilibrium3D(const Equilibrium3D&) = default;
70 0 : Equilibrium3D& operator=(const Equilibrium3D&) = default;
71 0 : Equilibrium3D(Equilibrium3D&&) = default;
72 0 : Equilibrium3D& operator=(Equilibrium3D&&) = default;
73 0 : ~Equilibrium3D() override = default;
74 :
75 0 : explicit Equilibrium3D(const EquilEos& underlying_eos)
76 : : underlying_eos_(underlying_eos){};
77 :
78 : EQUATION_OF_STATE_FORWARD_DECLARE_MEMBERS(Equilibrium3D, 3)
79 :
80 0 : std::unique_ptr<EquationOfState<EquilEos::is_relativistic, 3>> get_clone()
81 : const override;
82 :
83 0 : bool is_equal(
84 : const EquationOfState<EquilEos::is_relativistic, 3>& rhs) const override;
85 :
86 : /// \brief Returns `true` if the EOS is barotropic
87 1 : bool is_barotropic() const override { return false; }
88 :
89 : /// \brief Returns `true` if the EOS is in beta-equilibrium
90 1 : bool is_equilibrium() const override { return true; }
91 :
92 0 : bool operator==(const Equilibrium3D<EquilEos>& rhs) const;
93 :
94 0 : bool operator!=(const Equilibrium3D<EquilEos>& rhs) const;
95 : /// @{
96 : /*!
97 : * Computes the electron fraction in beta-equilibrium \f$Y_e^{\rm eq}\f$ from
98 : * the rest mass density \f$\rho\f$ and the temperature \f$T\f$.
99 : */
100 1 : Scalar<double> equilibrium_electron_fraction_from_density_temperature(
101 : const Scalar<double>& rest_mass_density,
102 : const Scalar<double>& temperature) const override{
103 : return underlying_eos_
104 : .equilibrium_electron_fraction_from_density_temperature(
105 : rest_mass_density, temperature);
106 : }
107 :
108 1 : Scalar<DataVector> equilibrium_electron_fraction_from_density_temperature(
109 : const Scalar<DataVector>& rest_mass_density,
110 : const Scalar<DataVector>& temperature) const override {
111 : return underlying_eos_
112 : .equilibrium_electron_fraction_from_density_temperature(
113 : rest_mass_density, temperature);
114 : }
115 : /// @}
116 : //
117 :
118 0 : WRAPPED_PUPable_decl_base_template( // NOLINT
119 : SINGLE_ARG(EquationOfState<EquilEos::is_relativistic, 3>), Equilibrium3D);
120 :
121 : /// The lower bound of the electron fraction that is valid for this EOS
122 1 : double electron_fraction_lower_bound() const override { return 0.0; }
123 :
124 : /// The upper bound of the electron fraction that is valid for this EOS
125 1 : double electron_fraction_upper_bound() const override { return 1.0; }
126 :
127 : /// The lower bound of the rest mass density that is valid for this EOS
128 1 : double rest_mass_density_lower_bound() const override {
129 : return underlying_eos_.rest_mass_density_lower_bound();
130 : }
131 :
132 : /// The upper bound of the rest mass density that is valid for this EOS
133 1 : double rest_mass_density_upper_bound() const override {
134 : return underlying_eos_.rest_mass_density_upper_bound();
135 : }
136 :
137 : /// The lower bound of the temperature that is valid for this EOS
138 1 : double temperature_lower_bound() const override {
139 : return underlying_eos_.temperature_lower_bound();
140 : }
141 :
142 : /// The upper bound of the temperature that is valid for this EOS
143 1 : double temperature_upper_bound() const override {
144 : return underlying_eos_.temperature_upper_bound();
145 : }
146 :
147 : /// The lower bound of the specific internal energy that is valid for this EOS
148 : /// at the given rest mass density \f$\rho\f$ and electron fraction \f$Y_e\f$
149 1 : double specific_internal_energy_lower_bound(
150 : const double rest_mass_density,
151 : const double /*electron_fraction*/) const override {
152 : return underlying_eos_.specific_internal_energy_lower_bound(
153 : rest_mass_density);
154 : }
155 :
156 : /// The upper bound of the specific internal energy that is valid for this EOS
157 : /// at the given rest mass density \f$\rho\f$
158 1 : double specific_internal_energy_upper_bound(
159 : const double rest_mass_density,
160 : const double /*electron_fraction*/) const override {
161 : return underlying_eos_.specific_internal_energy_upper_bound(
162 : rest_mass_density);
163 : }
164 :
165 : /// The lower bound of the specific enthalpy that is valid for this EOS
166 1 : double specific_enthalpy_lower_bound() const override {
167 : return underlying_eos_.specific_enthalpy_lower_bound();
168 : }
169 :
170 : /// The baryon mass for this EoS
171 1 : double baryon_mass() const override { return underlying_eos_.baryon_mass(); }
172 :
173 : private:
174 : EQUATION_OF_STATE_FORWARD_DECLARE_MEMBER_IMPLS(3)
175 0 : EquilEos underlying_eos_;
176 : };
177 : /// \cond
178 : template <typename EquilEos>
179 : PUP::able::PUP_ID EquationsOfState::Equilibrium3D<EquilEos>::my_PUP_ID = 0;
180 : /// \endcond
181 : } // namespace EquationsOfState
|