opm-common
GasPvtMultiplexer.hpp
Go to the documentation of this file.
1 // -*- mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 // vi: set et ts=4 sw=4 sts=4:
3 /*
4  This file is part of the Open Porous Media project (OPM).
5 
6  OPM is free software: you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation, either version 2 of the License, or
9  (at your option) any later version.
10 
11  OPM is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with OPM. If not, see <http://www.gnu.org/licenses/>.
18 
19  Consult the COPYING file in the top-level source directory of this
20  module for the precise wording of the license and the list of
21  copyright holders.
22 */
27 #ifndef OPM_GAS_PVT_MULTIPLEXER_HPP
28 #define OPM_GAS_PVT_MULTIPLEXER_HPP
29 
37 
38 #include <functional>
39 namespace Opm {
40 
41 class EclipseState;
42 class Schedule;
43 
44 #define OPM_GAS_PVT_MULTIPLEXER_CALL(codeToCall, ...) \
45  switch (gasPvtApproach_) { \
46  case GasPvtApproach::DryGas: { \
47  auto& pvtImpl = getRealPvt<GasPvtApproach::DryGas>(); \
48  codeToCall; \
49  __VA_ARGS__; \
50  } \
51  case GasPvtApproach::DryHumidGas: { \
52  auto& pvtImpl = getRealPvt<GasPvtApproach::DryHumidGas>(); \
53  codeToCall; \
54  __VA_ARGS__; \
55  } \
56  case GasPvtApproach::WetHumidGas: { \
57  auto& pvtImpl = getRealPvt<GasPvtApproach::WetHumidGas>(); \
58  codeToCall; \
59  __VA_ARGS__; \
60  } \
61  case GasPvtApproach::WetGas: { \
62  auto& pvtImpl = getRealPvt<GasPvtApproach::WetGas>(); \
63  codeToCall; \
64  __VA_ARGS__; \
65  } \
66  case GasPvtApproach::ThermalGas: { \
67  auto& pvtImpl = getRealPvt<GasPvtApproach::ThermalGas>(); \
68  codeToCall; \
69  __VA_ARGS__; \
70  } \
71  case GasPvtApproach::Co2Gas: { \
72  auto& pvtImpl = getRealPvt<GasPvtApproach::Co2Gas>(); \
73  codeToCall; \
74  __VA_ARGS__; \
75  } \
76  case GasPvtApproach::H2Gas: { \
77  auto& pvtImpl = getRealPvt<GasPvtApproach::H2Gas>(); \
78  codeToCall; \
79  __VA_ARGS__; \
80  } \
81  default: \
82  case GasPvtApproach::NoGas: \
83  throw std::logic_error("Not implemented: Gas PVT of this deck!"); \
84  }
85 
86 enum class GasPvtApproach {
87  NoGas,
88  DryGas,
89  DryHumidGas,
90  WetHumidGas,
91  WetGas,
92  ThermalGas,
93  Co2Gas,
94  H2Gas
95 };
96 
107 template <class Scalar, bool enableThermal = true>
109 {
110 public:
112  : gasPvtApproach_(GasPvtApproach::NoGas)
113  , realGasPvt_(nullptr, [](void*){})
114  {
115  }
116 
117  GasPvtMultiplexer(GasPvtApproach approach, void* realGasPvt)
118  : gasPvtApproach_(approach)
119  , realGasPvt_(realGasPvt, [this](void* ptr){ deleter(ptr); })
120  { }
121 
123  {
124  *this = data;
125  }
126 
127  ~GasPvtMultiplexer() = default;
128 
129  bool mixingEnergy() const
130  {
131  return gasPvtApproach_ == GasPvtApproach::ThermalGas;
132  }
133 
134  bool isActive() const {
135  return gasPvtApproach_ != GasPvtApproach::NoGas;
136  }
137 
143  void initFromState(const EclipseState& eclState, const Schedule& schedule);
144 
145  void setApproach(GasPvtApproach gasPvtAppr);
146 
147  void initEnd();
148 
152  unsigned numRegions() const;
153 
154  void setVapPars(const Scalar par1, const Scalar par2);
155 
159  Scalar gasReferenceDensity(unsigned regionIdx) const;
160 
164  template <class Evaluation>
165  Evaluation internalEnergy(unsigned regionIdx,
166  const Evaluation& temperature,
167  const Evaluation& pressure,
168  const Evaluation& Rv,
169  const Evaluation& Rvw) const
170  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.internalEnergy(regionIdx, temperature, pressure, Rv, Rvw)); }
171 
172  Scalar hVap(unsigned regionIdx) const;
173 
177  template <class Evaluation = Scalar>
178  Evaluation viscosity(unsigned regionIdx,
179  const Evaluation& temperature,
180  const Evaluation& pressure,
181  const Evaluation& Rv,
182  const Evaluation& Rvw ) const
183  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.viscosity(regionIdx, temperature, pressure, Rv, Rvw)); }
184 
188  template <class Evaluation = Scalar>
189  Evaluation saturatedViscosity(unsigned regionIdx,
190  const Evaluation& temperature,
191  const Evaluation& pressure) const
192  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedViscosity(regionIdx, temperature, pressure)); }
193 
197  template <class Evaluation = Scalar>
198  Evaluation inverseFormationVolumeFactor(unsigned regionIdx,
199  const Evaluation& temperature,
200  const Evaluation& pressure,
201  const Evaluation& Rv,
202  const Evaluation& Rvw) const
203  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.inverseFormationVolumeFactor(regionIdx, temperature, pressure, Rv, Rvw)); }
204 
208  template <class FluidState, class LhsEval = typename FluidState::ValueType>
209  std::pair<LhsEval, LhsEval>
210  inverseFormationVolumeFactorAndViscosity(const FluidState& fluidState, unsigned regionIdx)
211  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.inverseFormationVolumeFactorAndViscosity(fluidState, regionIdx)); }
212 
216  template <class Evaluation = Scalar>
217  Evaluation saturatedInverseFormationVolumeFactor(unsigned regionIdx,
218  const Evaluation& temperature,
219  const Evaluation& pressure) const
220  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedInverseFormationVolumeFactor(regionIdx, temperature, pressure)); }
221 
225  template <class Evaluation = Scalar>
226  Evaluation saturatedOilVaporizationFactor(unsigned regionIdx,
227  const Evaluation& temperature,
228  const Evaluation& pressure) const
229  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedOilVaporizationFactor(regionIdx, temperature, pressure)); }
230 
234  template <class Evaluation = Scalar>
235  Evaluation saturatedOilVaporizationFactor(unsigned regionIdx,
236  const Evaluation& temperature,
237  const Evaluation& pressure,
238  const Evaluation& oilSaturation,
239  const Evaluation& maxOilSaturation) const
240  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedOilVaporizationFactor(regionIdx, temperature, pressure, oilSaturation, maxOilSaturation)); }
241 
245  template <class Evaluation = Scalar>
246  Evaluation saturatedWaterVaporizationFactor(unsigned regionIdx,
247  const Evaluation& temperature,
248  const Evaluation& pressure) const
249  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedWaterVaporizationFactor(regionIdx, temperature, pressure)); }
250 
254  template <class Evaluation = Scalar>
255  Evaluation saturatedWaterVaporizationFactor(unsigned regionIdx,
256  const Evaluation& temperature,
257  const Evaluation& pressure,
258  const Evaluation& saltConcentration) const
259  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturatedWaterVaporizationFactor(regionIdx, temperature, pressure, saltConcentration)); }
260 
269  template <class Evaluation = Scalar>
270  Evaluation saturationPressure(unsigned regionIdx,
271  const Evaluation& temperature,
272  const Evaluation& Rv) const
273  { OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.saturationPressure(regionIdx, temperature, Rv)); }
274 
278  template <class Evaluation>
279  Evaluation diffusionCoefficient(const Evaluation& temperature,
280  const Evaluation& pressure,
281  unsigned compIdx) const
282  {
283  OPM_GAS_PVT_MULTIPLEXER_CALL(return pvtImpl.diffusionCoefficient(temperature, pressure, compIdx));
284  }
285 
291  GasPvtApproach approach() const
292  { return gasPvtApproach_; }
293 
294  // get the parameter object for the dry gas case
295  template <GasPvtApproach approachV>
296  typename std::enable_if<approachV == GasPvtApproach::DryGas, DryGasPvt<Scalar> >::type& getRealPvt()
297  {
298  assert(approach() == approachV);
299  return *static_cast<DryGasPvt<Scalar>* >(realGasPvt_.get());
300  }
301 
302  template <GasPvtApproach approachV>
303  typename std::enable_if<approachV == GasPvtApproach::DryGas, const DryGasPvt<Scalar> >::type& getRealPvt() const
304  {
305  assert(approach() == approachV);
306  return *static_cast<const DryGasPvt<Scalar>* >(realGasPvt_.get());
307  }
308 
309  // get the parameter object for the dry humid gas case
310  template <GasPvtApproach approachV>
311  typename std::enable_if<approachV == GasPvtApproach::DryHumidGas, DryHumidGasPvt<Scalar> >::type& getRealPvt()
312  {
313  assert(approach() == approachV);
314  return *static_cast<DryHumidGasPvt<Scalar>* >(realGasPvt_.get());
315  }
316 
317  template <GasPvtApproach approachV>
318  typename std::enable_if<approachV == GasPvtApproach::DryHumidGas, const DryHumidGasPvt<Scalar> >::type& getRealPvt() const
319  {
320  assert(approach() == approachV);
321  return *static_cast<const DryHumidGasPvt<Scalar>* >(realGasPvt_.get());
322  }
323 
324  // get the parameter object for the wet humid gas case
325  template <GasPvtApproach approachV>
326  typename std::enable_if<approachV == GasPvtApproach::WetHumidGas, WetHumidGasPvt<Scalar> >::type& getRealPvt()
327  {
328  assert(approach() == approachV);
329  return *static_cast<WetHumidGasPvt<Scalar>* >(realGasPvt_.get());
330  }
331 
332  template <GasPvtApproach approachV>
333  typename std::enable_if<approachV == GasPvtApproach::WetHumidGas, const WetHumidGasPvt<Scalar> >::type& getRealPvt() const
334  {
335  assert(approach() == approachV);
336  return *static_cast<const WetHumidGasPvt<Scalar>* >(realGasPvt_.get());
337  }
338 
339  // get the parameter object for the wet gas case
340  template <GasPvtApproach approachV>
341  typename std::enable_if<approachV == GasPvtApproach::WetGas, WetGasPvt<Scalar> >::type& getRealPvt()
342  {
343  assert(approach() == approachV);
344  return *static_cast<WetGasPvt<Scalar>* >(realGasPvt_.get());
345  }
346 
347  template <GasPvtApproach approachV>
348  typename std::enable_if<approachV == GasPvtApproach::WetGas, const WetGasPvt<Scalar> >::type& getRealPvt() const
349  {
350  assert(approach() == approachV);
351  return *static_cast<const WetGasPvt<Scalar>* >(realGasPvt_.get());
352  }
353 
354  // get the parameter object for the thermal gas case
355  template <GasPvtApproach approachV>
356  typename std::enable_if<approachV == GasPvtApproach::ThermalGas, GasPvtThermal<Scalar> >::type& getRealPvt()
357  {
358  assert(approach() == approachV);
359  return *static_cast<GasPvtThermal<Scalar>* >(realGasPvt_.get());
360  }
361  template <GasPvtApproach approachV>
362  typename std::enable_if<approachV == GasPvtApproach::ThermalGas, const GasPvtThermal<Scalar> >::type& getRealPvt() const
363  {
364  assert(approach() == approachV);
365  return *static_cast<const GasPvtThermal<Scalar>* >(realGasPvt_.get());
366  }
367 
368  template <GasPvtApproach approachV>
369  typename std::enable_if<approachV == GasPvtApproach::Co2Gas, Co2GasPvt<Scalar> >::type& getRealPvt()
370  {
371  assert(approach() == approachV);
372  return *static_cast<Co2GasPvt<Scalar>* >(realGasPvt_.get());
373  }
374 
375  template <GasPvtApproach approachV>
376  typename std::enable_if<approachV == GasPvtApproach::Co2Gas, const Co2GasPvt<Scalar> >::type& getRealPvt() const
377  {
378  assert(approach() == approachV);
379  return *static_cast<const Co2GasPvt<Scalar>* >(realGasPvt_.get());
380  }
381 
382  template <GasPvtApproach approachV>
383  typename std::enable_if<approachV == GasPvtApproach::H2Gas, H2GasPvt<Scalar> >::type& getRealPvt()
384  {
385  assert(approach() == approachV);
386  return *static_cast<H2GasPvt<Scalar>* >(realGasPvt_.get());
387  }
388 
389  template <GasPvtApproach approachV>
390  typename std::enable_if<approachV == GasPvtApproach::H2Gas, const H2GasPvt<Scalar> >::type& getRealPvt() const
391  {
392  assert(approach() == approachV);
393  return *static_cast<const H2GasPvt<Scalar>* >(realGasPvt_.get());
394  }
395 
396  const void* realGasPvt() const { return realGasPvt_.get(); }
397 
398  GasPvtMultiplexer<Scalar,enableThermal>&
399  operator=(const GasPvtMultiplexer<Scalar,enableThermal>& data);
400 
401 private:
402  using UniqueVoidPtrWithDeleter = std::unique_ptr<void, std::function<void(void*)>>;
403 
404  template <class ConcreteGasPvt> UniqueVoidPtrWithDeleter makeGasPvt();
405 
406  template <class ConcretePvt> UniqueVoidPtrWithDeleter copyPvt(const UniqueVoidPtrWithDeleter&);
407 
408  GasPvtApproach gasPvtApproach_{GasPvtApproach::NoGas};
409  UniqueVoidPtrWithDeleter realGasPvt_;
410 
411  void deleter(void* ptr);
412 };
413 
414 } // namespace Opm
415 
416 #endif
unsigned numRegions() const
Return the number of PVT regions which are considered by this PVT-object.
Definition: GasPvtMultiplexer.cpp:41
Evaluation saturatedViscosity(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure) const
Returns the dynamic viscosity [Pa s] of oil saturated gas given a set of parameters.
Definition: GasPvtMultiplexer.hpp:189
This class represents the Pressure-Volume-Temperature relations of the gas phase with vaporized water...
Definition: Schedule.hpp:100
Evaluation saturatedOilVaporizationFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure, const Evaluation &oilSaturation, const Evaluation &maxOilSaturation) const
Returns the oil vaporization factor [m^3/m^3] of oil saturated gas.
Definition: GasPvtMultiplexer.hpp:235
This class represents the Pressure-Volume-Temperature relations of the gas phas with vaporized oil...
GasPvtApproach approach() const
Returns the concrete approach for calculating the PVT relations.
Definition: GasPvtMultiplexer.hpp:291
Evaluation internalEnergy(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure, const Evaluation &Rv, const Evaluation &Rvw) const
Returns the specific enthalpy [J/kg] of gas given a set of parameters.
Definition: GasPvtMultiplexer.hpp:165
This class represents the Pressure-Volume-Temperature relations of the gas phase with vaporized oil a...
Evaluation saturatedInverseFormationVolumeFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure) const
Returns the formation volume factor [-] of oil saturated gas given a set of parameters.
Definition: GasPvtMultiplexer.hpp:217
This class implements a small container which holds the transmissibility mulitpliers for all the face...
Definition: Exceptions.hpp:30
This class represents the Pressure-Volume-Temperature relations of the gas phase in the black-oil mod...
Definition: GasPvtMultiplexer.hpp:108
This class implements temperature dependence of the PVT properties of gas.
Evaluation inverseFormationVolumeFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure, const Evaluation &Rv, const Evaluation &Rvw) const
Returns the formation volume factor [-] of the fluid phase.
Definition: GasPvtMultiplexer.hpp:198
Definition: EclipseState.hpp:66
Scalar gasReferenceDensity(unsigned regionIdx) const
Return the reference density which are considered by this PVT-object.
Definition: GasPvtMultiplexer.cpp:57
Evaluation saturatedWaterVaporizationFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure, const Evaluation &saltConcentration) const
Returns the water vaporization factor [m^3/m^3] of water saturated gas.
Definition: GasPvtMultiplexer.hpp:255
Evaluation saturatedWaterVaporizationFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure) const
Returns the water vaporization factor [m^3/m^3] of water saturated gas.
Definition: GasPvtMultiplexer.hpp:246
This class represents the Pressure-Volume-Temperature relations of the gas phase for H2...
Evaluation diffusionCoefficient(const Evaluation &temperature, const Evaluation &pressure, unsigned compIdx) const
Calculate the binary molecular diffusion coefficient for a component in a fluid phase [mol^2 * s / (k...
Definition: GasPvtMultiplexer.hpp:279
Evaluation saturatedOilVaporizationFactor(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure) const
Returns the oil vaporization factor [m^3/m^3] of oil saturated gas.
Definition: GasPvtMultiplexer.hpp:226
Evaluation viscosity(unsigned regionIdx, const Evaluation &temperature, const Evaluation &pressure, const Evaluation &Rv, const Evaluation &Rvw) const
Returns the dynamic viscosity [Pa s] of the fluid phase given a set of parameters.
Definition: GasPvtMultiplexer.hpp:178
void initFromState(const EclipseState &eclState, const Schedule &schedule)
Initialize the parameters for gas using an ECL deck.
Definition: GasPvtMultiplexer.cpp:72
This class represents the Pressure-Volume-Temperature relations of the gas phase for CO2...
Evaluation saturationPressure(unsigned regionIdx, const Evaluation &temperature, const Evaluation &Rv) const
Returns the saturation pressure of the gas phase [Pa] depending on its mass fraction of the oil compo...
Definition: GasPvtMultiplexer.hpp:270
This class represents the Pressure-Volume-Temperature relations of the gas phase without vaporized oi...
Definition: DryGasPvt.hpp:47
This class represents the Pressure-Volume-Temperature relations of the gas phase without vaporized oi...
std::pair< LhsEval, LhsEval > inverseFormationVolumeFactorAndViscosity(const FluidState &fluidState, unsigned regionIdx)
Returns the formation volume factor [-] and viscosity [Pa s] of the fluid phase.
Definition: GasPvtMultiplexer.hpp:210