Skip to content

psychrometrics

PsychrometricCalculator

Class to calculate psychrometric variables using CoolProp.

Source code in shimeri/psychrometrics.py
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
class PsychrometricCalculator:
    """Class to calculate psychrometric variables using CoolProp."""

    def __init__(self, pressure: float = 101.325):
        """Initialize the Psychrometrics class.

        Args:
            pressure: Atmospheric pressure (kPa)
        """
        self.pressure = pressure
        self._pressure_pa = pressure * 1000  # Convert to Pa for CoolProp

    def get_all(
        self,
        db: ArrayLike = np.nan,
        wb: ArrayLike = np.nan,
        rh: ArrayLike = np.nan,
        hr: ArrayLike = np.nan,
        en: ArrayLike = np.nan,
    ) -> tuple[
        Union[NDArray[np.float64], float],
        Union[NDArray[np.float64], float],
        Union[NDArray[np.float64], float],
        Union[NDArray[np.float64], float],
        Union[NDArray[np.float64], float],
    ]:
        """
        Calculate all psychrometric variables given any two of them.

        This function takes in any two of the five psychrometric variables (dry bulb temperature, wet bulb temperature,
        relative humidity, humidty ratio, specific air enthalpy) and calculates the remaining three. The inputs are
        broadcasted to have the same shape, and the calculation is performed element-wise.

        Args:
            db: Dry bulb temperature (degC).
            wb: Wet bulb temperature (degC).
            rh: Relative humidity (%).
            hr: Humidty ratio in g/kg.
            en: Specific air enthalpy in kJ/kg.

        Returns:
            A tuple of five numpy arrays or float, each representing one of the psychrometric variables. The arrays have the same shape as the broadcasted input arrays.

        Raises:
            ValueError: If the number of provided variables is not exactly two.
        """
        # Check args number (2 vars of 5)
        provided_args_number = sum(
            np.isfinite(arg).any() for arg in [db, wb, rh, hr, en]
        )
        if provided_args_number != 2:
            raise ValueError("Input 2 Variables of 5.")

        db, wb, rh, hr, en = np.broadcast_arrays(db, wb, rh, hr, en)
        original_shape = db.shape
        db = db.flatten().astype(float)
        wb = wb.flatten().astype(float)
        rh = rh.flatten().astype(float)
        hr = hr.flatten().astype(float)
        en = en.flatten().astype(float)

        # Build input parameters for HAPropsSI
        inputs = []

        if np.isfinite(db).any():
            inputs.append(("T", db + 273.15))  # degC to K
        if np.isfinite(wb).any():
            inputs.append(("B", wb + 273.15))  # degC to K (wet bulb)
        if np.isfinite(rh).any():
            inputs.append(("R", rh / 100))  # % to fraction
        if np.isfinite(hr).any():
            inputs.append(("W", hr / 1000))  # g/kg to kg/kg
        if np.isfinite(en).any():
            inputs.append(("H", en * 1000))  # kJ/kg to J/kg

        input1_name, input1_val = inputs[0]
        input2_name, input2_val = inputs[1]

        # Calculate all outputs using HAPropsSI
        db_out = (
            HAPropsSI(
                "T",
                input1_name,
                input1_val,
                input2_name,
                input2_val,
                "P",
                self._pressure_pa,
            )
            - 273.15
        )  # K to degC
        wb_out = (
            HAPropsSI(
                "B",
                input1_name,
                input1_val,
                input2_name,
                input2_val,
                "P",
                self._pressure_pa,
            )
            - 273.15
        )  # K to degC
        rh_out = (
            HAPropsSI(
                "R",
                input1_name,
                input1_val,
                input2_name,
                input2_val,
                "P",
                self._pressure_pa,
            )
            * 100
        )  # fraction to %
        hr_out = (
            HAPropsSI(
                "W",
                input1_name,
                input1_val,
                input2_name,
                input2_val,
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg
        en_out = (
            HAPropsSI(
                "H",
                input1_name,
                input1_val,
                input2_name,
                input2_val,
                "P",
                self._pressure_pa,
            )
            / 1000
        )  # J/kg to kJ/kg

        # Ensure outputs are numpy arrays
        db_out = np.atleast_1d(db_out)
        wb_out = np.atleast_1d(wb_out)
        rh_out = np.atleast_1d(rh_out)
        hr_out = np.atleast_1d(hr_out)
        en_out = np.atleast_1d(en_out)

        if db_out.size == 1:
            return db_out[0], wb_out[0], rh_out[0], hr_out[0], en_out[0]
        return (
            db_out.reshape(original_shape),
            wb_out.reshape(original_shape),
            rh_out.reshape(original_shape),
            hr_out.reshape(original_shape),
            en_out.reshape(original_shape),
        )

    def get_en_from_db_hr(self, db: ArrayLike, hr: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate specific air enthalpy from dry bulb temperature and humidity ratio.

        Args:
            db: Dry bulb temperature (degC).
            hr: Humidity ratio (g/kg).

        Returns:
            Specific air enthalpy (kJ/kg).
        """
        db, hr = np.broadcast_arrays(db, hr)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "H",
                "T",
                np.asarray(db).flatten() + 273.15,
                "W",
                np.asarray(hr).flatten() / 1000,
                "P",
                self._pressure_pa,
            )
            / 1000
        )  # J/kg to kJ/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_en_from_db_rh(self, db: ArrayLike, rh: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate specific air enthalpy from dry bulb temperature and relative humidity.

        Args:
            db: Dry bulb temperature (degC).
            rh: Relative humidity (%).
        Returns:
            Specific air enthalpy (kJ/kg).
        """
        db, rh = np.broadcast_arrays(db, rh)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "H",
                "T",
                np.asarray(db).flatten() + 273.15,
                "R",
                np.asarray(rh).flatten() / 100,
                "P",
                self._pressure_pa,
            )
            / 1000
        )  # J/kg to kJ/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_hr_from_db_en(self, db: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate humidity ratio from dry bulb temperature and specific air enthalpy.

        Args:
            db: Dry bulb temperature (degC).
            en: Specific air enthalpy (kJ/kg).

        Returns:
            Humidity ratio (g/kg).
        """
        db, en = np.broadcast_arrays(db, en)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "W",
                "T",
                np.asarray(db).flatten() + 273.15,
                "H",
                np.asarray(en).flatten() * 1000,
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_hr_from_db_rh(self, db: ArrayLike, rh: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate humidity ratio from dry bulb temperature and relative humidity.

        Args:
            db: Dry bulb temperature (degC).
            rh: Relative humidity (%).

        Returns:
            Humidity ratio (g/kg).
        """
        db, rh = np.broadcast_arrays(db, rh)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "W",
                "T",
                np.asarray(db).flatten() + 273.15,
                "R",
                np.asarray(rh).flatten() / 100,
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_rh_from_db_hr(self, db: ArrayLike, hr: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate relative humidity from dry bulb temperature and humidity ratio.

        Args:
            db: Dry bulb temperature (degC).
            hr: Humidity ratio (g/kg).

        Returns:
            Relative humidity (%).
        """
        db, hr = np.broadcast_arrays(db, hr)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "R",
                "T",
                np.asarray(db).flatten() + 273.15,
                "W",
                np.asarray(hr).flatten() / 1000,
                "P",
                self._pressure_pa,
            )
            * 100
        )  # fraction to %

        return np.atleast_1d(result).reshape(original_shape)

    def get_db_from_hr_en(self, hr: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate dry bulb temperature from humidity ratio and specific air enthalpy.

        Args:
            hr: Humidity ratio (g/kg).
            en: Specific air enthalpy (kJ/kg).

        Returns:
            Dry bulb temperature (degC).
        """
        hr, en = np.broadcast_arrays(hr, en)
        original_shape = hr.shape

        result = (
            HAPropsSI(
                "T",
                "W",
                np.asarray(hr).flatten() / 1000,
                "H",
                np.asarray(en).flatten() * 1000,
                "P",
                self._pressure_pa,
            )
            - 273.15
        )  # K to degC

        return np.atleast_1d(result).reshape(original_shape)

    def get_db_from_rh_en(self, rh: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate dry bulb temperature from relative humidity and specific air enthalpy.

        Args:
            rh: Relative humidity (%).
            en: Specific air enthalpy (kJ/kg).
        Returns:
            Dry bulb temperature (degC).
        """
        rh, en = np.broadcast_arrays(rh, en)
        original_shape = rh.shape

        result = (
            HAPropsSI(
                "T",
                "R",
                np.asarray(rh).flatten() / 100,
                "H",
                np.asarray(en).flatten() * 1000,
                "P",
                self._pressure_pa,
            )
            - 273.15
        )  # K to degC

        return np.atleast_1d(result).reshape(original_shape)

    def get_hr_from_db_wb(self, db: ArrayLike, wb: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate humidity ratio from dry bulb temperature and wet bulb temperature.

        Args:
            db: Dry bulb temperature (degC).
            wb: Wet bulb temperature (degC).

        Returns:
            Humidity ratio (g/kg).
        """
        db, wb = np.broadcast_arrays(db, wb)
        original_shape = db.shape

        result = (
            HAPropsSI(
                "W",
                "T",
                np.asarray(db).flatten() + 273.15,
                "B",
                np.asarray(wb).flatten() + 273.15,
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_hr_from_rh_en(self, rh: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate humidity ratio from relative humidity and specific air enthalpy.

        Args:
            rh: Relative humidity (%).
            en: Specific air enthalpy (kJ/kg).
        Returns:
            Humidity ratio (g/kg).
        """
        rh, en = np.broadcast_arrays(rh, en)
        original_shape = rh.shape

        result = (
            HAPropsSI(
                "W",
                "R",
                np.asarray(rh).flatten() / 100,
                "H",
                np.asarray(en).flatten() * 1000,
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg

        return np.atleast_1d(result).reshape(original_shape)

    def get_hr_from_pw(self, pw: ArrayLike) -> NDArray[np.float64]:
        """
        Calculate humidity ratio from partial pressure of water vapor.

        Args:
            pw: Partial pressure of water vapor (kPa).

        Returns:
            Humidity ratio (g/kg).
        """
        pw = np.asarray(pw)
        original_shape = pw.shape
        is_scalar = pw.ndim == 0

        result = (
            HAPropsSI(
                "W",
                "P_w",
                np.atleast_1d(pw).flatten() * 1000,  # kPa to Pa
                "T",
                293.15,  # Reference temperature (20°C)
                "P",
                self._pressure_pa,
            )
            * 1000
        )  # kg/kg to g/kg

        if is_scalar:
            return np.atleast_1d(result)[0]
        return np.atleast_1d(result).reshape(original_shape)

__init__(pressure=101.325)

Initialize the Psychrometrics class.

Parameters:

Name Type Description Default
pressure float

Atmospheric pressure (kPa)

101.325
Source code in shimeri/psychrometrics.py
def __init__(self, pressure: float = 101.325):
    """Initialize the Psychrometrics class.

    Args:
        pressure: Atmospheric pressure (kPa)
    """
    self.pressure = pressure
    self._pressure_pa = pressure * 1000  # Convert to Pa for CoolProp

get_all(db=np.nan, wb=np.nan, rh=np.nan, hr=np.nan, en=np.nan)

Calculate all psychrometric variables given any two of them.

This function takes in any two of the five psychrometric variables (dry bulb temperature, wet bulb temperature, relative humidity, humidty ratio, specific air enthalpy) and calculates the remaining three. The inputs are broadcasted to have the same shape, and the calculation is performed element-wise.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

nan
wb ArrayLike

Wet bulb temperature (degC).

nan
rh ArrayLike

Relative humidity (%).

nan
hr ArrayLike

Humidty ratio in g/kg.

nan
en ArrayLike

Specific air enthalpy in kJ/kg.

nan

Returns:

Type Description
tuple[Union[NDArray[float64], float], Union[NDArray[float64], float], Union[NDArray[float64], float], Union[NDArray[float64], float], Union[NDArray[float64], float]]

A tuple of five numpy arrays or float, each representing one of the psychrometric variables. The arrays have the same shape as the broadcasted input arrays.

Raises:

Type Description
ValueError

If the number of provided variables is not exactly two.

Source code in shimeri/psychrometrics.py
def get_all(
    self,
    db: ArrayLike = np.nan,
    wb: ArrayLike = np.nan,
    rh: ArrayLike = np.nan,
    hr: ArrayLike = np.nan,
    en: ArrayLike = np.nan,
) -> tuple[
    Union[NDArray[np.float64], float],
    Union[NDArray[np.float64], float],
    Union[NDArray[np.float64], float],
    Union[NDArray[np.float64], float],
    Union[NDArray[np.float64], float],
]:
    """
    Calculate all psychrometric variables given any two of them.

    This function takes in any two of the five psychrometric variables (dry bulb temperature, wet bulb temperature,
    relative humidity, humidty ratio, specific air enthalpy) and calculates the remaining three. The inputs are
    broadcasted to have the same shape, and the calculation is performed element-wise.

    Args:
        db: Dry bulb temperature (degC).
        wb: Wet bulb temperature (degC).
        rh: Relative humidity (%).
        hr: Humidty ratio in g/kg.
        en: Specific air enthalpy in kJ/kg.

    Returns:
        A tuple of five numpy arrays or float, each representing one of the psychrometric variables. The arrays have the same shape as the broadcasted input arrays.

    Raises:
        ValueError: If the number of provided variables is not exactly two.
    """
    # Check args number (2 vars of 5)
    provided_args_number = sum(
        np.isfinite(arg).any() for arg in [db, wb, rh, hr, en]
    )
    if provided_args_number != 2:
        raise ValueError("Input 2 Variables of 5.")

    db, wb, rh, hr, en = np.broadcast_arrays(db, wb, rh, hr, en)
    original_shape = db.shape
    db = db.flatten().astype(float)
    wb = wb.flatten().astype(float)
    rh = rh.flatten().astype(float)
    hr = hr.flatten().astype(float)
    en = en.flatten().astype(float)

    # Build input parameters for HAPropsSI
    inputs = []

    if np.isfinite(db).any():
        inputs.append(("T", db + 273.15))  # degC to K
    if np.isfinite(wb).any():
        inputs.append(("B", wb + 273.15))  # degC to K (wet bulb)
    if np.isfinite(rh).any():
        inputs.append(("R", rh / 100))  # % to fraction
    if np.isfinite(hr).any():
        inputs.append(("W", hr / 1000))  # g/kg to kg/kg
    if np.isfinite(en).any():
        inputs.append(("H", en * 1000))  # kJ/kg to J/kg

    input1_name, input1_val = inputs[0]
    input2_name, input2_val = inputs[1]

    # Calculate all outputs using HAPropsSI
    db_out = (
        HAPropsSI(
            "T",
            input1_name,
            input1_val,
            input2_name,
            input2_val,
            "P",
            self._pressure_pa,
        )
        - 273.15
    )  # K to degC
    wb_out = (
        HAPropsSI(
            "B",
            input1_name,
            input1_val,
            input2_name,
            input2_val,
            "P",
            self._pressure_pa,
        )
        - 273.15
    )  # K to degC
    rh_out = (
        HAPropsSI(
            "R",
            input1_name,
            input1_val,
            input2_name,
            input2_val,
            "P",
            self._pressure_pa,
        )
        * 100
    )  # fraction to %
    hr_out = (
        HAPropsSI(
            "W",
            input1_name,
            input1_val,
            input2_name,
            input2_val,
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg
    en_out = (
        HAPropsSI(
            "H",
            input1_name,
            input1_val,
            input2_name,
            input2_val,
            "P",
            self._pressure_pa,
        )
        / 1000
    )  # J/kg to kJ/kg

    # Ensure outputs are numpy arrays
    db_out = np.atleast_1d(db_out)
    wb_out = np.atleast_1d(wb_out)
    rh_out = np.atleast_1d(rh_out)
    hr_out = np.atleast_1d(hr_out)
    en_out = np.atleast_1d(en_out)

    if db_out.size == 1:
        return db_out[0], wb_out[0], rh_out[0], hr_out[0], en_out[0]
    return (
        db_out.reshape(original_shape),
        wb_out.reshape(original_shape),
        rh_out.reshape(original_shape),
        hr_out.reshape(original_shape),
        en_out.reshape(original_shape),
    )

get_db_from_hr_en(hr, en)

Calculate dry bulb temperature from humidity ratio and specific air enthalpy.

Parameters:

Name Type Description Default
hr ArrayLike

Humidity ratio (g/kg).

required
en ArrayLike

Specific air enthalpy (kJ/kg).

required

Returns:

Type Description
NDArray[float64]

Dry bulb temperature (degC).

Source code in shimeri/psychrometrics.py
def get_db_from_hr_en(self, hr: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate dry bulb temperature from humidity ratio and specific air enthalpy.

    Args:
        hr: Humidity ratio (g/kg).
        en: Specific air enthalpy (kJ/kg).

    Returns:
        Dry bulb temperature (degC).
    """
    hr, en = np.broadcast_arrays(hr, en)
    original_shape = hr.shape

    result = (
        HAPropsSI(
            "T",
            "W",
            np.asarray(hr).flatten() / 1000,
            "H",
            np.asarray(en).flatten() * 1000,
            "P",
            self._pressure_pa,
        )
        - 273.15
    )  # K to degC

    return np.atleast_1d(result).reshape(original_shape)

get_db_from_rh_en(rh, en)

Calculate dry bulb temperature from relative humidity and specific air enthalpy.

Parameters:

Name Type Description Default
rh ArrayLike

Relative humidity (%).

required
en ArrayLike

Specific air enthalpy (kJ/kg).

required

Returns: Dry bulb temperature (degC).

Source code in shimeri/psychrometrics.py
def get_db_from_rh_en(self, rh: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate dry bulb temperature from relative humidity and specific air enthalpy.

    Args:
        rh: Relative humidity (%).
        en: Specific air enthalpy (kJ/kg).
    Returns:
        Dry bulb temperature (degC).
    """
    rh, en = np.broadcast_arrays(rh, en)
    original_shape = rh.shape

    result = (
        HAPropsSI(
            "T",
            "R",
            np.asarray(rh).flatten() / 100,
            "H",
            np.asarray(en).flatten() * 1000,
            "P",
            self._pressure_pa,
        )
        - 273.15
    )  # K to degC

    return np.atleast_1d(result).reshape(original_shape)

get_en_from_db_hr(db, hr)

Calculate specific air enthalpy from dry bulb temperature and humidity ratio.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
hr ArrayLike

Humidity ratio (g/kg).

required

Returns:

Type Description
NDArray[float64]

Specific air enthalpy (kJ/kg).

Source code in shimeri/psychrometrics.py
def get_en_from_db_hr(self, db: ArrayLike, hr: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate specific air enthalpy from dry bulb temperature and humidity ratio.

    Args:
        db: Dry bulb temperature (degC).
        hr: Humidity ratio (g/kg).

    Returns:
        Specific air enthalpy (kJ/kg).
    """
    db, hr = np.broadcast_arrays(db, hr)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "H",
            "T",
            np.asarray(db).flatten() + 273.15,
            "W",
            np.asarray(hr).flatten() / 1000,
            "P",
            self._pressure_pa,
        )
        / 1000
    )  # J/kg to kJ/kg

    return np.atleast_1d(result).reshape(original_shape)

get_en_from_db_rh(db, rh)

Calculate specific air enthalpy from dry bulb temperature and relative humidity.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
rh ArrayLike

Relative humidity (%).

required

Returns: Specific air enthalpy (kJ/kg).

Source code in shimeri/psychrometrics.py
def get_en_from_db_rh(self, db: ArrayLike, rh: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate specific air enthalpy from dry bulb temperature and relative humidity.

    Args:
        db: Dry bulb temperature (degC).
        rh: Relative humidity (%).
    Returns:
        Specific air enthalpy (kJ/kg).
    """
    db, rh = np.broadcast_arrays(db, rh)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "H",
            "T",
            np.asarray(db).flatten() + 273.15,
            "R",
            np.asarray(rh).flatten() / 100,
            "P",
            self._pressure_pa,
        )
        / 1000
    )  # J/kg to kJ/kg

    return np.atleast_1d(result).reshape(original_shape)

get_hr_from_db_en(db, en)

Calculate humidity ratio from dry bulb temperature and specific air enthalpy.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
en ArrayLike

Specific air enthalpy (kJ/kg).

required

Returns:

Type Description
NDArray[float64]

Humidity ratio (g/kg).

Source code in shimeri/psychrometrics.py
def get_hr_from_db_en(self, db: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate humidity ratio from dry bulb temperature and specific air enthalpy.

    Args:
        db: Dry bulb temperature (degC).
        en: Specific air enthalpy (kJ/kg).

    Returns:
        Humidity ratio (g/kg).
    """
    db, en = np.broadcast_arrays(db, en)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "W",
            "T",
            np.asarray(db).flatten() + 273.15,
            "H",
            np.asarray(en).flatten() * 1000,
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg

    return np.atleast_1d(result).reshape(original_shape)

get_hr_from_db_rh(db, rh)

Calculate humidity ratio from dry bulb temperature and relative humidity.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
rh ArrayLike

Relative humidity (%).

required

Returns:

Type Description
NDArray[float64]

Humidity ratio (g/kg).

Source code in shimeri/psychrometrics.py
def get_hr_from_db_rh(self, db: ArrayLike, rh: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate humidity ratio from dry bulb temperature and relative humidity.

    Args:
        db: Dry bulb temperature (degC).
        rh: Relative humidity (%).

    Returns:
        Humidity ratio (g/kg).
    """
    db, rh = np.broadcast_arrays(db, rh)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "W",
            "T",
            np.asarray(db).flatten() + 273.15,
            "R",
            np.asarray(rh).flatten() / 100,
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg

    return np.atleast_1d(result).reshape(original_shape)

get_hr_from_db_wb(db, wb)

Calculate humidity ratio from dry bulb temperature and wet bulb temperature.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
wb ArrayLike

Wet bulb temperature (degC).

required

Returns:

Type Description
NDArray[float64]

Humidity ratio (g/kg).

Source code in shimeri/psychrometrics.py
def get_hr_from_db_wb(self, db: ArrayLike, wb: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate humidity ratio from dry bulb temperature and wet bulb temperature.

    Args:
        db: Dry bulb temperature (degC).
        wb: Wet bulb temperature (degC).

    Returns:
        Humidity ratio (g/kg).
    """
    db, wb = np.broadcast_arrays(db, wb)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "W",
            "T",
            np.asarray(db).flatten() + 273.15,
            "B",
            np.asarray(wb).flatten() + 273.15,
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg

    return np.atleast_1d(result).reshape(original_shape)

get_hr_from_pw(pw)

Calculate humidity ratio from partial pressure of water vapor.

Parameters:

Name Type Description Default
pw ArrayLike

Partial pressure of water vapor (kPa).

required

Returns:

Type Description
NDArray[float64]

Humidity ratio (g/kg).

Source code in shimeri/psychrometrics.py
def get_hr_from_pw(self, pw: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate humidity ratio from partial pressure of water vapor.

    Args:
        pw: Partial pressure of water vapor (kPa).

    Returns:
        Humidity ratio (g/kg).
    """
    pw = np.asarray(pw)
    original_shape = pw.shape
    is_scalar = pw.ndim == 0

    result = (
        HAPropsSI(
            "W",
            "P_w",
            np.atleast_1d(pw).flatten() * 1000,  # kPa to Pa
            "T",
            293.15,  # Reference temperature (20°C)
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg

    if is_scalar:
        return np.atleast_1d(result)[0]
    return np.atleast_1d(result).reshape(original_shape)

get_hr_from_rh_en(rh, en)

Calculate humidity ratio from relative humidity and specific air enthalpy.

Parameters:

Name Type Description Default
rh ArrayLike

Relative humidity (%).

required
en ArrayLike

Specific air enthalpy (kJ/kg).

required

Returns: Humidity ratio (g/kg).

Source code in shimeri/psychrometrics.py
def get_hr_from_rh_en(self, rh: ArrayLike, en: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate humidity ratio from relative humidity and specific air enthalpy.

    Args:
        rh: Relative humidity (%).
        en: Specific air enthalpy (kJ/kg).
    Returns:
        Humidity ratio (g/kg).
    """
    rh, en = np.broadcast_arrays(rh, en)
    original_shape = rh.shape

    result = (
        HAPropsSI(
            "W",
            "R",
            np.asarray(rh).flatten() / 100,
            "H",
            np.asarray(en).flatten() * 1000,
            "P",
            self._pressure_pa,
        )
        * 1000
    )  # kg/kg to g/kg

    return np.atleast_1d(result).reshape(original_shape)

get_rh_from_db_hr(db, hr)

Calculate relative humidity from dry bulb temperature and humidity ratio.

Parameters:

Name Type Description Default
db ArrayLike

Dry bulb temperature (degC).

required
hr ArrayLike

Humidity ratio (g/kg).

required

Returns:

Type Description
NDArray[float64]

Relative humidity (%).

Source code in shimeri/psychrometrics.py
def get_rh_from_db_hr(self, db: ArrayLike, hr: ArrayLike) -> NDArray[np.float64]:
    """
    Calculate relative humidity from dry bulb temperature and humidity ratio.

    Args:
        db: Dry bulb temperature (degC).
        hr: Humidity ratio (g/kg).

    Returns:
        Relative humidity (%).
    """
    db, hr = np.broadcast_arrays(db, hr)
    original_shape = db.shape

    result = (
        HAPropsSI(
            "R",
            "T",
            np.asarray(db).flatten() + 273.15,
            "W",
            np.asarray(hr).flatten() / 1000,
            "P",
            self._pressure_pa,
        )
        * 100
    )  # fraction to %

    return np.atleast_1d(result).reshape(original_shape)