carbatpy ======== .. py:module:: carbatpy .. autoapi-nested-parse:: Top-level package for carbatpy. Submodules ---------- .. toctree:: :maxdepth: 1 /autoapi/carbatpy/cb_config/index /autoapi/carbatpy/helpers/index /autoapi/carbatpy/models/index /autoapi/carbatpy/optimizations/index /autoapi/carbatpy/optional/index /autoapi/carbatpy/utils/index Attributes ---------- .. autoapisummary:: carbatpy.TREND carbatpy.CB_DEFAULTS Classes ------- .. autoapisummary:: carbatpy.Fluid carbatpy.FluidModel carbatpy.FluidState carbatpy.FlowDeviceOld carbatpy.HeatExchanger carbatpy.Surrogate Functions --------- .. autoapisummary:: carbatpy.init_fluid Package Contents ---------------- .. py:data:: TREND .. py:data:: CB_DEFAULTS .. py:class:: Fluid(fluidmodel, composition=None, option=1) The Fluid class is used to set, get, and print states of a fluid with a given model (e.g. RefProp). The compounds are set in the fluidmodel, while the composition is also set here. The calculated values depend also on carbatpy.CB_DEFAULTS["Fluid_Defaults"]["Property_Names_Short"]. Generate a Fluid instance a FluidModel instance, the composition and an unused option has to be passed. :param fluidmodel: the instance of the property model to be used. :type fluidmodel: FluidModel :param composition: mole fractions of all compounds. The default is [1.0]. :type composition: list, optional :param option: unused. The default is 1. :type option: TYPE, optional :rtype: None. .. py:attribute:: fluidmodel .. py:attribute:: composition .. py:attribute:: properties :value: None .. py:attribute:: state_v :value: None .. py:attribute:: option :value: 1 .. py:attribute:: no_compounds .. py:attribute:: comp_mass .. py:attribute:: herr :value: 0 .. py:attribute:: props .. py:attribute:: val_dict .. py:method:: set_composition(composition, **kwargs) Mole fractions are set and mass fractions are calculated. Sets the self.composition used in the Fluid settings and the self.comp_mass TREND needs the mass fractions for specific (/kg) calculations. Thus calc_mass_fraction() is called. :param composition: mole fractions must sum up to 1. :type composition: list/numpy.array :param kwargs: - verbose : boolean, optional. Generate additional printig. The default is False. :type kwargs: dictionary, optional. :rtype: None. .. py:method:: calc_mass_fraction() mole to mass fractions for TREND .. py:method:: calc_mole_fraction(comp_mass) needed for x_liq and y_vap in TREND, therefore mass fraction passed as function argument. .. py:method:: set_state(values, given='TP', wanted=_THERMO_STRING, composition=None, **kwargs) Sets the state of a fluid and calculates the wanted properties. :param values: the two state parameter values. :type values: list[2] :param given: What are the two values (T,P,H,S,Q,V). The default is "TP". :type given: String, optional :param wanted: Which parameters shall be calculated? The default is _THERMO_STRING. :type wanted: String, optional :param composition: mole fraction of each compound, must sum up to 1. When empty, the last/actual value will be used. The default is []. :type composition: list, optional :param kwargs: dll_select : str, optional is passed to Refprop. The standard value is "2dll" using the faster REFPROP2dll function, not calculating the composition of different phases. The alternative "dll" is slower but does it. Throughout it is expected that compoitions are mole fractions and qualities in mass/mass. i_mass : int (0/1), optional should not be used, not tested. i_flag : int (0/1), optional should not be used, not tested. verbose : Boolean, optional leads to additional (printing) output. The default value is False. output : String, optional what shall be the return value, the "state" as list or an instance of the "FluidState". default is "state" :type kwargs: dictionary, optional :raises Exception: DESCRIPTION. :returns: DESCRIPTION. :rtype: TYPE .. py:method:: calc_q_mass(q, liq_x, liq_y) .. py:method:: set_state_v(values, given='TP', wanted=_THERMO_STRING, **kwargs) set many Fluid states with the values given as array(vector) :param values: the N value pairs to fix the states. :type values: numpy.array((N,2)) :param given: what are the input values?(T,P, Q, S,...). The default is "TP". :type given: String, optional :param wanted: with all the outputs wanted. The default is _THERMO_STRING. :type wanted: String, optional :param kwargs: This is optional and passed to REFPROP or TREND, depending on the props settings / chosen property model. (see set_state()) :type kwargs: dictionary optional :returns: **output** -- all the wanted properties for the N inputs. :rtype: numpy.array(N, n_wanted) .. py:method:: print_state() Print the actual state of the Fluid .. py:method:: calc_temp_mean(h_final) Calculate the thermodynamic mean temperature between the actual state and the final enthalpy along an isobaric (Delta h /Delta s) :param h_final: enthalpy of he final stat. :type h_final: float :returns: **temp_mean** -- the thermodynamic mean temperature. :rtype: float .. py:class:: FluidModel(fluid, composition=[1], **kwargs) Fluid model to be used Refprop or TREND Only model, chemical compunds units and for TREND some more values are set here. The mixture composition, state etc. is set in Fluid. For Class Fluidmodell a fluid (mixture) must be defined, the evaluation takes place with props, units can be set and an instance can be set, the latter is important, if more than one fluid is used. For Refprop: Initiates new instance for each fluid (mixture). :param fluid: as defined in the props (Model), for RefProp it is "fluid1 * fluid2 * fluid3". :type fluid: String :param composition: of working fluid (mixture), at this level only used for TREND :type composition: array :param \*\*kwargs: units, props, rp_inst, eos_ind, mix_ind, trendmodel, props_func (see dataclass FluidModelDefaults). For props="CUSTOM", props_func must be a callable with signature:: func(values, given) -> list[T, P, H, V, S, Q, U, ...] returning SI values (K, Pa, J/kg, m³/kg, J/kg/K, -, J/kg). :type \*\*kwargs: dict :rtype: None. .. py:attribute:: fluid .. py:attribute:: props :value: 'REFPROP' .. py:attribute:: units :value: 21 .. py:method:: fluid_to_list() Converts the fluid names string from Refprop to a list for TREND :returns: the fluid names in a list. :rtype: List of strings .. py:class:: FluidState(state, what, **kwargs) The thermodynamic state of a fluid is stored here. Which properties (T,p,h,v,s,q,...), depends on: carbatpy.CB_DEFAULTS["Fluid_Defaults"]["Property_Names_Short"] .. py:attribute:: props .. py:attribute:: verbose .. py:attribute:: liq_x .. py:attribute:: vap_y .. py:attribute:: total_z .. py:attribute:: state .. py:method:: state_to_dict() Convert the state properties to a dictionary name:value. .. py:function:: init_fluid(fluid, composition, **keywords) short way to define a Fluid and a FluidModel :param fluid: The species within the fluid. :type fluid: string :param composition: mole fraction for each fluid. :type composition: List :param \*\*keywords: all keywords needed for the FluidModel, if non-defaults shall be set. :type \*\*keywords: TYPE :returns: **actual_fluid** -- Instance of the actually set Fluid. :rtype: Fluid .. py:class:: FlowDeviceOld(fluid, p_out, m_dot, device_type='machine', **kwargs) Unified themodynamic calculations for single flow devices, Old version Calculate the output state and state changes for single flow devices :param fluid: The fluid at is entering state. :type fluid: cb.Fluid :param p_out: Output pressure in Pa. :type p_out: float :param m_dot: mass flow rate in kg/s. :type m_dot: float :param device_type: 'machine' for compressor/expander, 'pump', or 'throttle'. The default is "machine". :type device_type: TYPE, optional :param \*\*kwargs: Optional parameters for setting the configuration and parameters - plot info : dictionary,optional, default value is {} contains a Figure, an Axes, a list of What shall be plotted, a list with the colour/styles and a list with the labels must be passed. in "what", the two numbers coincide with the fluid THERMO order. The x-shift can be used in cycle calculations, to shift the curves, by the value (it will be added). The names in the dictionary are: "fig", "ax", "what","col", "label", "x-shift". - name : string, optional, the name of this specific device, the default is "compressor". - calc_type : string, optional, which method shall be used (e.g.: "const_eta", "const_h"), default is "const_eta". - calc_parameters : dictionary, optional, if further parameters have to be given for the calculation. the default is None. - verbose : Boolean, optional, the default is False. :type \*\*kwargs: dictionary DESCRIPTION. the self.output dictionary contains the exit state values, and work and power. The self.fluid is at the exit state. Check self.warning and self.warning_message. There is also a self.print_device function for inspection. If a figure is passed by plot_info the plot will be updated. :rtype: None. .. py:attribute:: fluid .. py:attribute:: p_out .. py:attribute:: m_dot .. py:attribute:: device_type :value: 'machine' .. py:attribute:: plot_info .. py:attribute:: name .. py:attribute:: calc_type .. py:attribute:: calc_parameters .. py:attribute:: verbose .. py:attribute:: warning :value: 0 .. py:attribute:: warning_message :value: 'All o.k.' .. py:attribute:: input .. py:attribute:: output :value: None .. py:property:: all .. py:method:: to_dict() .. py:method:: compressor() compressor or expander output state calculation so far only for a constant isentropic efficiency, according to the pressure change an expansion or compression is detected and handled. :param p_out: output pressure. :type p_out: float :param eta_s: isentropic efficiency. :type eta_s: float :param fluid: entering fluid, including properties, composition, and model. :type fluid: cb.Fluid :param m_dot: mass flow rate (in kg/s). Default is 1 :type m_dot: float, optional :param calc_type: how to calculate, so far, only one implemented. The default is "const_eta". :type calc_type: string, optional :param name: name of the device. The default is "compressor". :type name: string, optional :param plot_info: if not empty a Figure, an Axes, a list of What shall be plotted, a list with the colour/styles and a list with the labels must be passed. in "what", the two numbers coincide with the fluid THERMO order. The x-shift can be used in cycle calculations, to shift the curves, by the value (it will be added). The names in the dictionary are: "fig", "ax", "what","col", "label", "x-shift". Default is empty. :type plot_info: dictionary, optional :returns: * **state_out** (*array of float*) -- compressor output state containing [T,p,h,v,s,q]. * **work_specific** (*float*) -- work per kg of fluid, positive for compressor; units:J/kg. .. py:method:: pump() Calculate the exit state of a pump assuming an incompressible fluid. Only formulated for constant isentropic efficiency :param p_out: output pressure. :type p_out: float :param eta_s: isentropic efficiency. :type eta_s: float :param fluid: entering fluid, including properties, composition, and model. :type fluid: fprop.Fluid :param m_dot: mass flow rate (in kg/s). Default is 1 :type m_dot: float, optional :param calc_type: how to calculate, so far, only one implemented. The default is "const_eta". :type calc_type: string, optional :param name: name of the device. The default is "pump". :type name: string, optional :param plot_info: if not empty a Figure, an Axes, a list of What shall be plotted, a list with the colour/styles and a list with the labels must be passed. in "what", the two numbers coincide with the fluid THERMO order. The x-shift can be used in cycle calculations, to shift the curves, by the value (it will be added). The names in the dictionary are: "fig", "ax", "what","col", "label", "x-shift". Default is empty. :type plot_info: dictionary, optional :returns: * **state_out** (*array of float*) -- compressor output state containing [T,p,h,v,s,q]. * **work_specific** (*float*) -- work per kg of fluid, positive for compressor; units:J/kg. .. py:method:: throttle() throttle output state calculation so far only for a constant enthalpy :param p_out: output pressure. :type p_out: float :param fluid: entering fluid, including properties, composition, and model. :type fluid: fprop.Fluid :param m_dot: mass flow rate (in kg/s). Default is 1 :type m_dot: float, optional :param calc_type: how to calculate, so far, only one implemented. The default is "const_h". :type calc_type: string, optional :param name: name of the device. The default is "throttle". :type name: string, optional :param plot_info: if not empty a Figure, an Axes, a list of What shall be plotted, a list with the colour/styles and a list with the labels must be passed. in "what", the two numbers coincide with the fluid THERMO order. The x-shift can be used in cycle calculations, to shift the curves, by the value (it will be added). The names in the dictionary are: "fig", "ax", "what","col", "label", "x-shift". Default is empty. :type plot_info: dictionary, optional :returns: **state_out** -- compressor output state containing [T,p,h,v,s,q]. :rtype: array of float .. py:method:: plot_temp_h_flow() plotting a T-H-dot diagram for simple flows (compressor, throttle etc.) :param _state_in: entering state [T,p,h,v,s,...]. :type _state_in: np.array :param _state_out: exiting state. :type _state_out: np.array :param _m_dot: mass flow rate (kg/s). :type _m_dot: float :param _plot_info: if not empty a Figure, an Axes, a list of What shall be plotted, a list with the colour/styles and a list with the labels must be passed. in "what", the two numbers coincide with the fluid THERMO order. The x-shift can be used in cycle calculations, to shift the curves, by the value (it will be added). The names in the dictionary are: "fig", "ax", "what","col", "label", "x-shift". :type _plot_info: dictionary :rtype: None. .. py:method:: print_device() .. py:method:: state_w_p() .. py:class:: HeatExchanger(fluids, inlet_states, mdot, resolution, ht_method, pl_method) Static heat exchanger model for counterflow configurations. Supports double-pipe and monoblock geometries. Heat exchanger profiles are computed by integrating coupled enthalpy and pressure ODEs along the tube length using ``scipy.integrate.solve_ivp``. Two inlet-state conventions are available: - **One-side IVP** (:meth:`calc_IVP_one_side`): Both inlet states are provided for the *same* side (inlet–outlet pair). Avoids the internal root-finding step and is the recommended approach. - **Two-side IVP** (:meth:`calc_IVP`): True counterflow setup — inlet states are given for *both* fluid inlets (left and right end). Requires an internal root-find to determine the unknown starting conditions. Geometry Options ---------------- - **Double-pipe** (:meth:`geo_double_pipe`): Annular secondary-fluid channel around an inner tube carrying the working fluid. - **Monoblock** (:meth:`geo_monoblock`): Two parallel tubes embedded in a solid conductive block. Thermal coupling is via the block material, using the VDI Heat Atlas shape factor for two eccentric cylinders. :param fluids: Two-element list ``[working_fluid, secondary_fluid]``. Each fluid must expose a ``set_state`` method compatible with carbatpy.fprop. :type fluids: list of fluid objects :param inlet_states: Two-element list ``[state_in_wf, state_in_sf]``. Each state is the standard carbatpy property array (T, p, h, v, s, q, u, …). :type inlet_states: list of array_like :param mdot: Two-element list ``[mdot_wf, mdot_sf]``. Mass flow rates in kg/s. :type mdot: list of float :param resolution: Number of spatial evaluation points along the heat exchanger length. :type resolution: int :param ht_method: Heat transfer correlation for the working fluid passed to ``heat_transfer.alpha_km``. Example: ``"Deng_et_al-2019"``. :type ht_method: str :param pl_method: Pressure-loss correlation for the working fluid passed to ``heat_transfer.alpha_km``. Example: ``"Macdonald_et_al-2016"``. :type pl_method: str .. attribute:: state_array_wf Fluid-property states along the heat exchanger for the working fluid. :type: ndarray, shape (n, n_props) .. attribute:: state_array_sf Fluid-property states along the heat exchanger for the secondary fluid. :type: ndarray, shape (n, n_props) .. attribute:: x Axial positions [m] corresponding to the state arrays. :type: ndarray .. attribute:: alpha_wf Local heat transfer coefficients of the working fluid [W/(m²·K)]. :type: list of float .. attribute:: alpha_sf Local heat transfer coefficients of the secondary fluid [W/(m²·K)]. :type: list of float .. attribute:: dpdl_wf Local pressure-loss gradients of the working fluid [Pa/m]. :type: list of float .. attribute:: dpdl_sf Local pressure-loss gradients of the secondary fluid [Pa/m]. :type: list of float .. attribute:: termination_flag Name of the termination-event function that stopped the ODE solver, or ``None`` if the solver reached the end of the integration interval. :type: str or None .. attribute:: termination_position Axial position [m] at which termination occurred, or ``None``. :type: float or None .. rubric:: Examples Double-pipe condenser solved with the one-side IVP method: >>> import carbatpy as cb >>> from class_he import HeatExchanger >>> fluid1 = cb.init_fluid("Butane * CO2", [0.8, 0.2]) >>> fluid2 = cb.fprop.init_fluid("water", [1]) >>> st1_in = fluid1.set_state([3e6, 1], "PQ") >>> st2_in = fluid2.set_state([st1_in[0] - 10, 3e5], "TP", cb.fprop._TRANS_STRING) >>> he = HeatExchanger( ... fluids=[fluid1, fluid2], ... inlet_states=[st1_in, st2_in], ... mdot=[0.01, 0.01], ... resolution=40, ... ht_method="Deng_et_al-2019", ... pl_method="Macdonald_et_al-2016", ... ) >>> he.geo_double_pipe(16e-3, 18e-3, 22e-3, 40e-3, 40, 15.4) >>> he.calc_IVP_one_side(case="wf_condensed") >>> he.diagram() .. seealso:: :obj:`heat_transfer` Heat transfer and pressure-loss correlations used internally by :meth:`thermal_resistance`. .. py:attribute:: fluids .. py:attribute:: input_state_wf .. py:attribute:: input_state_sf .. py:attribute:: mdot_wf .. py:attribute:: mdot_sf .. py:attribute:: resolution .. py:attribute:: dT_wall :value: 5 .. py:attribute:: ht_method .. py:attribute:: pl_method .. py:method:: geo_monoblock(d_wf, d_sf, r, l, lam_block) Set monoblock heat exchanger geometry. Two parallel circular tubes are embedded in a solid conductive block. The thermal coupling between them is computed via the VDI Heat Atlas (2013) shape factor for two cylinders in an infinite medium (Table E1-3). :param d_wf: Inner diameter of the working-fluid tube [m]. :type d_wf: float :param d_sf: Inner diameter of the secondary-fluid tube [m]. :type d_sf: float :param r: Centre-to-centre distance between the two tubes [m]. :type r: float :param l: Length of the block (and tubes) [m]. :type l: float :param lam_block: Thermal conductivity of the block material [W/(m·K)]. :type lam_block: float .. rubric:: Notes The conduction shape factor for two cylinders in an infinite medium (VDI Heat Atlas 2013, E1 Table 3) is: .. math:: S = \frac{2\pi}{\mathrm{arccosh}\! \left(\frac{r^2 - r_{wf}^2 - r_{sf}^2} {2\, r_{wf}\, r_{sf}}\right)} where :math:`r_{wf} = d_{wf}/2` and :math:`r_{sf} = d_{sf}/2`. .. py:method:: geo_double_pipe(di, Di, da, Da, l, lam_tube) Set double-pipe heat exchanger geometry. The working fluid flows through the inner tube; the secondary fluid flows counter-currently through the annular gap between inner and outer tube. :param di: Inner diameter of the inner tube (working-fluid side) [m]. :type di: float :param Di: Outer diameter of the inner tube [m]. :type Di: float :param da: Inner diameter of the outer tube (secondary-fluid side) [m]. :type da: float :param Da: Outer diameter of the outer tube [m]. :type Da: float :param l: Length of the pipe section [m]. :type l: float :param lam_tube: Thermal conductivity of the inner-tube wall material [W/(m·K)]. :type lam_tube: float .. rubric:: Notes The total heat transfer area referenced to the inner tube surface is set to :math:`A = \pi d_i l`. The thermal resistance network (per unit length) is: .. math:: R_{tot} = \underbrace{\frac{1}{\alpha_{sf}\, \pi D_i}}_{R_{sf}} + \underbrace{\frac{\ln(D_i/d_i)}{2\pi\lambda_{tube}}}_{R_{tube}} + \underbrace{\frac{1}{\alpha_{wf}\, \pi d_i}}_{R_{wf}} .. rubric:: Examples >>> he.geo_double_pipe(16e-3, 18e-3, 22e-3, 40e-3, 40, 15.4) .. py:method:: calc_IVP_one_side(verbose=False, wf_outlet=False, case=None, stop_value=0) Calculate the heat exchanger by integrating the governing ODEs. Both inlet states must be provided for the *same* physical side of the heat exchanger (i.e. an inlet–outlet pair, not two true inlets). The ``wf_outlet`` flag controls which end of the domain is used as the working-fluid inlet. This is the **recommended** calculation method because it avoids the internal root-finding step required by :meth:`calc_IVP`. :param verbose: If ``True``, print the solver status message. :type verbose: bool, default=False :param wf_outlet: Flow-direction flag. - ``False``: working-fluid inlet is at :math:`x = 0`. - ``True``: working-fluid inlet is at :math:`x = l` (outlet side). :type wf_outlet: bool, default=False :param case: Optional early-termination criterion. Supported values: - ``'sf_temperature_min'`` – stop when secondary-fluid temperature falls below ``stop_value`` [K]. - ``'sf_enthalpy_min'`` – stop when secondary-fluid enthalpy falls below ``stop_value`` [J/kg]. - ``'wf_enthalpy_min'`` – stop when working-fluid enthalpy falls below ``stop_value`` [J/kg]. - ``'wf_enthalpy_max'`` – stop when working-fluid enthalpy exceeds ``stop_value`` [J/kg]. - ``'wf_condensed'`` – stop when working fluid is fully condensed (vapour quality ≤ saturated-liquid enthalpy). - ``'wf_evaporated'`` – stop when working fluid is fully evaporated (vapour quality ≥ saturated-vapour enthalpy). :type case: str or None, default=None :param stop_value: Threshold value used by the selected ``case``. Unit depends on the chosen case (K or J/kg). :type stop_value: float, default=0 :returns: Results are stored in ``state_array_wf``, ``state_array_sf``, ``x``, ``alpha_wf``, ``alpha_sf``, ``dpdl_wf``, ``dpdl_sf``, ``termination_flag``, and ``termination_position``. :rtype: None .. rubric:: Examples >>> he.geo_double_pipe(16e-3, 18e-3, 22e-3, 40e-3, 40, 15.4) >>> he.calc_IVP_one_side(verbose=True, case="wf_condensed") >>> print(he.termination_flag) .. py:method:: calc_IVP(verbose=False, case=None, stop_value=0) Calculate the heat exchanger using true counterflow inlet conditions. .. note:: **Not recommended.** Use :meth:`calc_IVP_one_side` instead, which avoids the internal root-finding step and is more robust. Inlet states must be the true inlet states for *both* fluids — one at each end of the heat exchanger. An internal ``scipy.optimize.root`` call iterates on the unknown secondary-fluid state at :math:`x = 0` until the prescribed secondary-fluid inlet condition at :math:`x = l` is matched. :param verbose: If ``True``, print the root-finder result and solver status. :type verbose: bool, default=False :param case: Optional early-termination criterion (see :meth:`calc_IVP_one_side` for supported values). :type case: str or None, default=None :param stop_value: Threshold for the selected ``case``. :type stop_value: float, default=0 :returns: Results are stored in ``state_array_wf``, ``state_array_sf``, ``x``, ``alpha_wf``, ``alpha_sf``, ``dpdl_wf``, and ``dpdl_sf``. :rtype: None :raises ValueError: If the root-finder does not converge. .. py:method:: thermal_resistance(state_wf_x, state_sf_x) Calculate the local total thermal resistance and pressure-loss gradients. Dispatches to the correct resistance model based on ``self.geo_flag`` (``"double_pipe"`` or ``"monoblock"``), appends the local heat transfer coefficients and pressure-loss gradients to the instance lists, and updates ``self.dT_wall``. :param state_wf_x: Local carbatpy property array of the working fluid (T, p, h, …). :type state_wf_x: array_like :param state_sf_x: Local carbatpy property array of the secondary fluid (T, p, h, …). :type state_sf_x: array_like :returns: * **R_ges** (*float*) -- Total thermal resistance per unit length [(m·K)/W]. * **dp_wf** (*float*) -- Pressure-loss gradient of the working fluid [Pa/m]. * **dp_sf** (*float*) -- Pressure-loss gradient of the secondary fluid [Pa/m]. .. rubric:: Notes **Double-pipe** resistance network (per unit length): .. math:: R_{tot} = \frac{1}{\alpha_{sf}\,\pi D_i} + \frac{\ln(D_i/d_i)}{2\pi\lambda_{tube}} + \frac{1}{\alpha_{wf}\,\pi d_i} **Monoblock** resistance network (per unit length): .. math:: R_{tot} = \frac{1}{\alpha_{sf}\,\pi d_{sf}} + \frac{1}{\lambda_{block}\, S} + \frac{1}{\alpha_{wf}\,\pi d_{wf}} with the VDI shape factor :math:`S` from :meth:`geo_monoblock`. .. py:method:: diagram(ordinate=0, second_yaxis=False, save_dir=None, show_plot=False) Plot fluid-property profiles along the heat exchanger length. The abscissa is the axial coordinate :math:`x` [m]. The ordinate is selected by index, matching the column order of ``state_array_wf`` / ``state_array_sf``: - 0: Temperature [K] - 1: Pressure [Pa] - 2: Specific enthalpy [J/kg] - 3: Specific volume [m³/kg] - 4: Specific entropy [J/(kg·K)] - 5: Vapour quality [–] - 6: Specific internal energy [J/kg] - 7: Dynamic viscosity [Pa·s] - 8: Thermal conductivity [W/(m·K)] - 9: Prandtl number [–] - 10: Kinematic viscosity [m²/s] - 11: Molar mass [kg/mol] - 12: Speed of sound [m/s] :param ordinate: Column index of the property to plot (see list above). :type ordinate: int, default=0 :param second_yaxis: If ``True``, working and secondary fluid are plotted on separate y-axes (useful when the two fluids have very different scales). :type second_yaxis: bool, default=False :param save_dir: Directory path for saving the figure as a PNG file. If ``None``, the figure is only displayed. :type save_dir: str or None, default=None :param show_plot: If "True", plots are shown. :type show_plot: bool, default=False :rtype: None .. rubric:: Examples >>> he.calc_IVP_one_side() >>> he.diagram() # temperature profile >>> he.diagram(ordinate=1, second_yaxis=True) # pressure, dual axes >>> he.diagram(ordinate=2, save_dir=r"C:/results") # save enthalpy plot .. py:method:: calculate_arrays(save_dir=None) Export calculation results to CSV files and a termination-event log. Writes three files to ``save_dir``: - ``wf.csv``: Working-fluid state array with columns ``T, p, h, v, s, q, u, alpha_wf, dpdl_wf, tcx, vis``. ``tcx`` and ``vis`` are the saturated-liquid thermal conductivity and viscosity where the vapour quality is ≥ 0; otherwise 0. - ``sf.csv``: Secondary-fluid state array with columns ``T, p, h, v, s, q, u, eta, tcx, Pr, cp, ws, M, alpha_sf, dpdl_sf``. - ``termination_event.txt``: Plain-text log of ``termination_flag`` and ``termination_position``. :param save_dir: Absolute path to an existing directory where the files will be saved. :type save_dir: str :returns: * **df_wf** (*DataFrame*) * **df_wf** (*DataFrame*) .. py:class:: Surrogate(title) .. py:attribute:: title .. py:method:: train_surrogate(DF, features_list, targets_list, split=0.2, random_state=42, hypo='def_hyperparameter.yaml', verbose=False) train MLP surrogate from dataframe with chosen features and targets, uses minmaxscaler and 'r2', 'neg_root_mean_squared_error' for scoring, the latter for refitting :param DF: DESCRIPTION. :type DF: TYPE :param features_list: DESCRIPTION. :type features_list: TYPE :param targets_list: DESCRIPTION. :type targets_list: TYPE :param split: DESCRIPTION. The default is 0.2. :type split: TYPE, optional :param random_state: DESCRIPTION. The default is 42. :type random_state: TYPE, optional :param hypo: DESCRIPTION. The default is "def_hyperparameter.yaml". :type hypo: TYPE, optional :returns: * **Y_test** (*TYPE DataFrame*) -- DESCRIPTION. test targets * **Y_pred** (*TYPE*) -- DESCRIPTION. predicted targets .. py:method:: save(path='default') save model :param path: DESCRIPTION. The default is CARBATPY_RES_DIR :type path: TYPE, optional :rtype: None. .. py:method:: load(path) .. py:method:: predict(DF_new_x) use existing surrogate to predict new data :param DF_new_x: DESCRIPTION. :type DF_new_x: TYPE :raises ValueError: DESCRIPTION. needs to contain features of model DESCRIPTION. does not extrapolate :returns: * **y** (*TYPE*) -- DESCRIPTION. target results * **DF_y** (*TYPE*) -- DESCRIPTION. target results