Cantera  4.0.0a1
Loading...
Searching...
No Matches
ReactorDelegator.h
Go to the documentation of this file.
1//! @file ReactorDelegator.h
2
3// This file is part of Cantera. See License.txt in the top-level directory or
4// at https://cantera.org/license.txt for license and copyright information.
5
6#ifndef CT_REACTORDELEGATOR_H
7#define CT_REACTORDELEGATOR_H
8
9#include "Reactor.h"
13
14namespace Cantera
15{
16
17//! An abstract base class for providing access to protected capabilities
18//! Reactor objects from delegate methods, which would normally only be able to
19//! access public Reactor members.
20//!
21//! Actual implementations of these methods are found in the templated
22//! ReactorDelegator class. The purpose of this base class is so these methods
23//! can be accessed by casting a Reactor* to a ReactorAccessor* without needing
24//! to know the specific kind of Reactor at compilation time.
26{
27public:
28 //! Set the number of equations represented by this reactor
29 virtual void setNEq(size_t n) = 0;
30
31 //! Get the net rate of volume change (for example, from moving walls) [m^3/s]
32 virtual double expansionRate() const = 0;
33
34 //! Set the net rate of volume change (for example, from moving walls) [m^3/s]
35 virtual void setExpansionRate(double v) = 0;
36
37 //! Get the net heat transfer rate (for example, through walls) into the
38 //! reactor [W]. This value is initialized and calculated as part of
39 //! Reactor::evalWalls().
40 virtual double heatRate() const = 0;
41
42 //! Set the net heat transfer rate (for example, through walls) into the
43 //! reactor [W]. For a value set using this method to affect the calculations done
44 //! by Reactor::eval, this method should be called in either a "replace" or "after"
45 //! delegate for Reactor::evalWalls().
46 virtual void setHeatRate(double q) = 0;
47
48 //! @copydoc ReactorBase::surfaceProductionRates
49 virtual span<double> surfaceProductionRates() = 0;
50};
51
52//! Delegate methods of the Reactor class to external functions
53//! @ingroup reactorGroup
54template <class R>
55class ReactorDelegator : public Delegator, public R, public ReactorAccessor
56{
57public:
58 template <class... Args>
59 ReactorDelegator(Args&&... args)
60 : R(std::forward<Args>(args)...)
61 {
62 install("initialize", m_initialize, [this](double t0) { R::initialize(t0); });
63 install("getState", m_getState,
64 [this](std::array<size_t, 1> sizes, double* y) { R::getState(y); });
65 install("updateState", m_updateState,
66 [this](std::array<size_t, 1> sizes, double* y) { R::updateState(y); });
67 install("updateConnected", m_updateConnected,
68 [this](bool updatePressure) { R::updateConnected(updatePressure); });
69 install("eval", m_eval,
70 [this](std::array<size_t, 2> sizes, double t, double* LHS, double* RHS) {
71 R::eval(t, LHS, RHS);
72 }
73 );
74 if constexpr (std::is_base_of<Reactor, R>::value) {
75 install("evalWalls", m_evalWalls, [this](double t) { R::evalWalls(t); });
76 }
77 install("componentName", m_componentName,
78 [this](size_t k) { return R::componentName(k); });
79 install("componentIndex", m_componentIndex,
80 [this](const string& nm) { return R::componentIndex(nm); });
81 }
82
83 // Overrides of Reactor methods
84
85 string type() const override {
86 return fmt::format("Extensible{}", R::type());
87 }
88
89 void initialize(double t0) override {
90 m_initialize(t0);
91 }
92
93 void getState(double* y) override {
94 std::array<size_t, 1> sizes{R::neq()};
95 m_getState(sizes, y);
96 }
97
98 void updateState(double* y) override {
99 std::array<size_t, 1> sizes{R::neq()};
100 m_updateState(sizes, y);
101 }
102
103 void updateConnected(bool updatePressure) override {
104 m_updateConnected(updatePressure);
105 }
106
107 void eval(double t, double* LHS, double* RHS) override {
108 std::array<size_t, 2> sizes{R::neq(), R::neq()};
109 m_eval(sizes, t, LHS, RHS);
110 }
111
112 void evalWalls(double t) override {
113 if constexpr (std::is_base_of<Reactor, R>::value) {
114 m_evalWalls(t);
115 } else {
117 }
118 }
119
120 string componentName(size_t k) override {
121 return m_componentName(k);
122 }
123
124 size_t componentIndex(const string& nm) const override {
125 return m_componentIndex(nm);
126 }
127
128 // Public access to protected Reactor variables needed by derived classes
129
130 void setNEq(size_t n) override {
131 R::m_nv = n;
132 }
133
134 double expansionRate() const override {
135 if constexpr (std::is_base_of<Reactor, R>::value) {
136 return R::m_vdot;
137 } else {
138 throw NotImplementedError("ReactorDelegator::expansionRate",
139 "Expansion rate is undefined for reactors of type '{}'.", type());
140 }
141 }
142
143 void setExpansionRate(double v) override {
144 if constexpr (std::is_base_of<Reactor, R>::value) {
145 R::m_vdot = v;
146 } else {
147 throw NotImplementedError("ReactorDelegator::setExpansionRate",
148 "Expansion rate is undefined for reactors of type '{}'.", type());
149 }
150 }
151
152 double heatRate() const override {
153 if constexpr (std::is_base_of<Reactor, R>::value) {
154 return R::m_Qdot;
155 } else {
156 throw NotImplementedError("ReactorDelegator::heatRate",
157 "Heat rate is undefined for reactors of type '{}'.", type());
158 }
159 }
160
161 void setHeatRate(double q) override {
162 if constexpr (std::is_base_of<Reactor, R>::value) {
163 R::m_Qdot = q;
164 } else {
165 throw NotImplementedError("ReactorDelegator::setHeatRate",
166 "Heat rate is undefined for reactors of type '{}'.", type());
167 }
168 }
169
170 span<double> surfaceProductionRates() override {
171 return R::m_sdot;
172 }
173
174private:
175 function<void(double)> m_initialize;
176 function<void(std::array<size_t, 1>, double*)> m_getState;
177 function<void(std::array<size_t, 1>, double*)> m_updateState;
178 function<void(bool)> m_updateConnected;
179 function<void(std::array<size_t, 2>, double, double*, double*)> m_eval;
180 function<void(double)> m_evalWalls;
181 function<string(size_t)> m_componentName;
182 function<size_t(const string&)> m_componentIndex;
183};
184
185}
186#endif
Header file for class ReactorSurface.
Header for a simple thermodynamics model of a surface phase derived from ThermoPhase,...
Delegate member functions of a C++ class to externally-specified functions.
Definition Delegator.h:104
void install(const string &name, function< void()> &target, const function< void()> &func)
Install a function with the signature void() as being delegatable.
Definition Delegator.h:301
An error indicating that an unimplemented function has been called.
An abstract base class for providing access to protected capabilities Reactor objects from delegate m...
virtual void setNEq(size_t n)=0
Set the number of equations represented by this reactor.
virtual span< double > surfaceProductionRates()=0
Production rates on surfaces.
virtual void setHeatRate(double q)=0
Set the net heat transfer rate (for example, through walls) into the reactor [W].
virtual void setExpansionRate(double v)=0
Set the net rate of volume change (for example, from moving walls) [m^3/s].
virtual double heatRate() const =0
Get the net heat transfer rate (for example, through walls) into the reactor [W].
virtual double expansionRate() const =0
Get the net rate of volume change (for example, from moving walls) [m^3/s].
virtual void evalWalls(double t)
Evaluate contributions from walls connected to this reactor.
Delegate methods of the Reactor class to external functions.
void setNEq(size_t n) override
Set the number of equations represented by this reactor.
double heatRate() const override
Get the net heat transfer rate (for example, through walls) into the reactor [W].
double expansionRate() const override
Get the net rate of volume change (for example, from moving walls) [m^3/s].
span< double > surfaceProductionRates() override
Production rates on surfaces.
void setExpansionRate(double v) override
Set the net rate of volume change (for example, from moving walls) [m^3/s].
void setHeatRate(double q) override
Set the net heat transfer rate (for example, through walls) into the reactor [W].
Namespace for the Cantera kernel.
Definition AnyMap.cpp:595