CoolProp 8.0.0
An open-source fluid property and humid air property database
SVDSurfaceFactory.h
Go to the documentation of this file.
1#ifndef COOLPROP_SBTL_SVD_SURFACE_FACTORY_H
2#define COOLPROP_SBTL_SVD_SURFACE_FACTORY_H
3
4#include <cstddef>
5#include <cstdint>
6#include <optional>
7
12
13namespace CoolProp {
14namespace sbtl {
15
17{
19 bool verbose = false;
20};
21
22// Generic factory: walk the per-region (xnorm, log_p) grid, call HEOS
23// per cell via the spec's `update_state` + `read_property` callbacks,
24// build one SVD per (region, property), seal into an SVDSurface.
25//
26// SurfaceSpec is consumed (moved-from) so the unique_ptr boundary
27// curves it owns transfer cleanly into the new SVDSurface's regions.
28//
29// Throws on:
30// - empty spec.regions / spec.properties
31// - mismatched spec.input_pair vs the callbacks' assumed inputs
32// (only detectable if the callbacks throw at sampling time)
33// - SVDBuilder failures (rank-deficient, non-finite samples surviving
34// the row-fill, ...)
36
37// Preset SurfaceSpec builders for the two MVP input pairs. Each one
38// constructs:
39// - 2-region atlas (LIQUID, VAPOR) over [p_triple, p_crit]
40// - CubicSpline sat boundaries via SatBoundaryFactory
41// - The standard property list for that input pair
42// - Default NT=200, NR=800, rank=20 grid sizes
43//
44// Caller can then mutate the SurfaceSpec before calling
45// build_surface() (raise the rank for a hard fluid, swap a boundary
46// curve, add an extra output property, etc.).
47//
48// Subsequent phases ship DU / HS / PS / DT presets the same way — no
49// changes to build_surface() or downstream consumers.
50namespace presets {
51
52// Build-time knobs shared by the subcritical presets and the backend.
53// Bundling them in one struct means a future knob is a new field here
54// (plus where it is parsed and consumed) — NOT a new positional
55// parameter rippling through every preset signature, the dispatcher,
56// and every call site.
58{
59 std::size_t NT = 200; // points along the secondary (non-log) axis
60 std::size_t NR = 800; // points along the primary (log-p) axis
61 std::int32_t rank = 20; // SVD truncation rank
62 // Absolute-Pa lower-pressure bound for the PT / HmassP / PSmass
63 // surfaces (the backend's `pmin` option). nullopt -> default
64 // p_triple floor; must be >= p_triple (see
65 // subcritical_pressure_range). Ignored by the DmassT preset, which
66 // is temperature-indexed and has no pressure floor.
67 std::optional<double> p_min;
68};
69
70// HmassP_INPUTS preset. (a, b) = (p, h). Output properties: rho, T, s, u.
72
73// PT_INPUTS preset. (a, b) = (p, T). Output properties: rho, h, s, u.
74SurfaceSpec pt_subcritical(::CoolProp::AbstractState& heos, const PresetOptions& opts = {});
75
76// PSmass_INPUTS preset. (a, b) = (p, s). Output properties: rho, T, h, u.
77// Entropy analog of ph_subcritical: s is the secondary axis + query
78// input; the same region geometry (LIQUID/VAPOR/NC/SUPER, IF97 R2/R3/R5
79// split) applies with the build_s_* boundary curves.
80SurfaceSpec ps_subcritical(::CoolProp::AbstractState& heos, const PresetOptions& opts = {});
81
82// DmassT_INPUTS preset. (a, b) = (T, D). Output properties: p, h, s, u.
83//
84// Primary advantage over PT/PH: (D, T) is the Helmholtz EOS's native
85// coordinate, so every output property is a direct evaluation — no
86// inversion, no critical-region stiffness, no "cells with -760 MPa"
87// failure modes like BICUBIC's invert_single_phase_y on #1301.
88//
89// Geometry mirrors ph_subcritical: LIQUID + VAPOR sub-critical (T <
90// T_critical * 0.999), SUPER super-critical (T > T_critical * 1.001).
91// Secondary axis D bounded by rho_sat,L(T) / rho_sat,V(T) and
92// per-fluid HEOS-validity D-extents on the non-dome side.
93//
94// Anomaly handling: for fluids whose ρ_sat,L(T) curve has interior
95// extrema (water at T_anom ≈ 277 K, heavy water at ≈ 284 K), the
96// LIQUID region is split into N+1 sub-regions where N is the number
97// of extrema — each sub-region's T span lies inside one monotonic
98// piece of ρ_sat,L(T). Auto-detected via the source backend's
99// SuperAncillary `get_x_at_extrema()` on the rho_sat,L expansion;
100// gracefully falls back to a single LIQUID region when no SA is
101// available (REFPROP / IF97 sources, or fluids without a SA in
102// HEOS).
103SurfaceSpec dt_subcritical(::CoolProp::AbstractState& heos, const PresetOptions& opts = {});
104
105} // namespace presets
106
107} // namespace sbtl
108} // namespace CoolProp
109
110#endif // COOLPROP_SBTL_SVD_SURFACE_FACTORY_H