Coverage for src / CSET / operators / pressure.py: 100%

40 statements  

« prev     ^ index     » next       coverage.py v7.13.2, created at 2026-01-28 11:16 +0000

1# © Crown copyright, Met Office (2022-2026) and CSET contributors. 

2# 

3# Licensed under the Apache License, Version 2.0 (the "License"); 

4# you may not use this file except in compliance with the License. 

5# You may obtain a copy of the License at 

6# 

7# http://www.apache.org/licenses/LICENSE-2.0 

8# 

9# Unless required by applicable law or agreed to in writing, software 

10# distributed under the License is distributed on an "AS IS" BASIS, 

11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 

12# See the License for the specific language governing permissions and 

13# limitations under the License. 

14 

15"""Operators for pressure conversions.""" 

16 

17import iris.cube 

18import numpy as np 

19 

20from CSET._common import iter_maybe 

21from CSET.operators._atmospheric_constants import E0, KAPPA, P0 

22from CSET.operators.misc import convert_units 

23 

24 

25def vapour_pressure( 

26 temperature: iris.cube.Cube | iris.cube.CubeList, 

27) -> iris.cube.Cube | iris.cube.CubeList: 

28 r"""Calculate the vapour pressure of the atmosphere. 

29 

30 Arguments 

31 --------- 

32 temperature: iris.cube.Cube | iris.cube.CubeList 

33 Cubes of temperature to be converted into vapour pressure. 

34 Temperature must be provided in Kelvin. 

35 

36 Returns 

37 ------- 

38 iris.cube.Cube | iris.cube.CubeList 

39 Vapour pressure in hPa. 

40 

41 Notes 

42 ----- 

43 The vapour pressure represents the pressure exerted by water vapour on the 

44 atmosphere. It is related to atmospheric temperature through the 

45 Clausius-Clapeyron equation. There are several different formulations based 

46 on empirical relations that are used to calculate the vapour pressure. Here, 

47 we calculate the vapour pressure based on [Tetens30]_ equation: 

48 

49 .. math:: e = e_0 * exp\left(17.27\frac{T - 273.16}{T - 35.86}\right) 

50 

51 for e the vapour pressure, :math:`e_0` the saturation vapour pressure at 

52 a reference temperature of 273.15 K with a value of 6.1078 hPa, and T the 

53 temperature. 

54 

55 The temperature is provided in Kelvin, and the vapour pressure is returned 

56 in hPa. 

57 

58 If the (dry-bulb) temperature is used the value given by the vapour pressure 

59 will be the saturation vapour pressure. On the other hand, if the dewpoint 

60 temperature is used the vapour pressure will be calculated. 

61 

62 References 

63 ---------- 

64 .. [Tetens30] Tetens, O. (1930) "Über einige meteorologische Begriffe". 

65 Z. Geophys 6: 297-309. 

66 

67 Examples 

68 -------- 

69 >>> vapour_pressure = pressure.vapour_pressure(temperature) 

70 """ 

71 v_pressure = iris.cube.CubeList([]) 

72 for T in iter_maybe(temperature): 

73 es = T.copy() 

74 exponent = 17.27 * (T - 273.16) / (T - 35.86) 

75 es.data = E0 * np.exp(exponent.core_data()) 

76 es.units = "hPa" 

77 es.rename("vapour_pressure") 

78 v_pressure.append(es) 

79 if len(v_pressure) == 1: 

80 return v_pressure[0] 

81 else: 

82 return v_pressure 

83 

84 

85def vapour_pressure_from_relative_humidity( 

86 temperature: iris.cube.Cube | iris.cube.CubeList, 

87 relative_humidity: iris.cube.Cube | iris.cube.CubeList, 

88) -> iris.cube.Cube | iris.cube.CubeList: 

89 r"""Calculate the vapour pressure using relative humidity RH. 

90 

91 Arguments 

92 --------- 

93 temperature: iris.cube.Cube | iris.cube.CubeList 

94 Cubes of temperature to be converted into saturation vapour pressure. 

95 Temperature must be provided in Kelvin. 

96 relative_humidity: iris.cube.Cube | iris.cube.CubeList 

97 Cubes of relative humidity to be converted into vapour pressure. 

98 Relative humidity must be provided in percentage and 

99 will be converted to a decimal by the operator. 

100 

101 Returns 

102 ------- 

103 iris.cube.Cube | iris.cube.CubeList 

104 Vapour pressure in hPa. 

105 

106 Notes 

107 ----- 

108 The vapour pressure can be derived from the relative humidity and 

109 temperature based on the following relation 

110 

111 .. math:: e = RH * e_s 

112 

113 for e the vapour pressure, :math:`e_s` the saturation vapour pressure, 

114 and RH the relative humidity. 

115 

116 The relative humidity is converted to a decimal. The saturation vapour 

117 pressure is calculated using `pressure.vapour_pressure`. 

118 

119 Examples 

120 -------- 

121 >>> vapour_pressure = pressure.vapour_pressure_from_relative_humidity(temperature, relative_humidity) 

122 """ 

123 v_pressure = iris.cube.CubeList([]) 

124 for T, RH in zip( 

125 iter_maybe(temperature), iter_maybe(relative_humidity), strict=True 

126 ): 

127 RH = convert_units(RH, "1") 

128 vp = vapour_pressure(T) * RH 

129 vp.units = "hPa" 

130 vp.rename("vapour_pressure") 

131 v_pressure.append(vp) 

132 if len(v_pressure) == 1: 

133 return v_pressure[0] 

134 else: 

135 return v_pressure 

136 

137 

138def exner_pressure( 

139 pressure: iris.cube.Cube | iris.cube.CubeList, 

140) -> iris.cube.Cube | iris.cube.CubeList: 

141 r"""Calculate the exner pressure. 

142 

143 Arguments 

144 --------- 

145 pressure: iris.cube.Cube | iris.cube.CubeList 

146 Cubes of pressure to be converted. 

147 

148 Returns 

149 ------- 

150 iris.cube.Cube | iris.cube.CubeList 

151 Exner pressure. 

152 

153 Notes 

154 ----- 

155 The Exner pressure is also referred to as the Exner function. It is a 

156 dimensionless parameter that can be used either as a vertical coordinate or 

157 more frequently as a means to simplifying conversions between different 

158 parameters (e.g. Temperature and Potential Temperature; [Holton13]_). 

159 It is calculated as 

160 

161 .. math:: \Pi = \left(\frac{P}{P_0}\right)^{\frac{R_d}{c_p}} 

162 

163 for :math:`\Pi` the Exner Pressure, P the pressure in hPa, :math:`P_0` a reference pressure 

164 of 1000 hPa, :math:`R_d` the specific gas constant of dry air taken as 297 :math:`J kg^{-1} K^{-1}`, 

165 :math:`c_p` the specific heat capacity at constant pressure taken as 1005.7 :math:`J kg^{-1} K^{-1}`. 

166 

167 A value below one implies the pressure is higher than the reference pressure; 

168 values above one implies the pressure is lower than the reference pressure; a 

169 value of one implies the pressure is equal to the reference pressure. 

170 

171 References 

172 ---------- 

173 .. [Holton13] Holton, J.R. and Hakim G.J. (2013) "An Introduction to Dynamic 

174 Meteorology." 5th Edition, Burlington, MA, Elsevier Academic Press, 532 pp. 

175 

176 Examples 

177 -------- 

178 >>> Exner_pressure = pressure.exner_pressure(pressure) 

179 """ 

180 pi = iris.cube.CubeList([]) 

181 for P in iter_maybe(pressure): 

182 PI = P.copy() 

183 P = convert_units(P, "hPa") 

184 PI.data = (P.core_data() / P0) ** KAPPA 

185 PI.rename("exner_pressure") 

186 PI.units = "1" 

187 pi.append(PI) 

188 if len(pi) == 1: 

189 return pi[0] 

190 else: 

191 return pi