FV3 Bundle
gsw_sa_freezing_from_t.f90
Go to the documentation of this file.
1 !==========================================================================
2 elemental function gsw_sa_freezing_from_t (t, p, saturation_fraction)
3 !==========================================================================
4 !
5 ! Calculates the Absolute Salinity of seawater at the freezing temperature.
6 ! That is, the output is the Absolute Salinity of seawater, with the
7 ! fraction saturation_fraction of dissolved air, that is in equilibrium
8 ! with ice at in-situ temperature t and pressure p. If the input values
9 ! are such that there is no positive value of Absolute Salinity for which
10 ! seawater is frozen, the output is set to NaN.
11 !
12 ! t = in-situ Temperature (ITS-90) [ deg C ]
13 ! p = sea pressure [ dbar ]
14 ! ( i.e. absolute pressure - 10.1325 dbar )
15 ! saturation_fraction = the saturation fraction of dissolved air in
16 ! seawater
17 ! (i.e., saturation_fraction must be between 0 and 1, and the default
18 ! is 1, completely saturated)
19 !
20 ! sa_freezing_from_t = Absolute Salinity of seawater when it freezes, for
21 ! given input values of in situ temperature, pressure and
22 ! air saturation fraction. [ g/kg ]
23 !---------------------------------------------------------------------------
24 
28 
30 
31 use gsw_mod_kinds
32 
33 implicit none
34 
35 real (r8), intent(in) :: t, p, saturation_fraction
36 
37 real (r8) :: gsw_sa_freezing_from_t
38 
39 integer :: i_iter
40 real (r8) :: f, sa, sa_mean, sa_old, t_freezing_zero_sa, tfreezing_sa
41 
42 integer, parameter :: number_of_iterations = 2
43 
44 ! This is the band of sa within +- 2.5 g/kg of sa = 0, which we treat
45 ! differently in calculating the initial values of both SA and dCT_dSA.
46 real (r8), parameter :: sa_cut_off = 2.5_r8
47 
48 character (*), parameter :: func_name = "gsw_sa_freezing_from_t"
49 
50 ! Find t > t_freezing_zero_SA. If this is the case, the input values
51 ! represent seawater that is not frozen (at any positive SA).
52 t_freezing_zero_sa = gsw_t_freezing_exact(0.0_r8,p,saturation_fraction)
53 if (t .gt. t_freezing_zero_sa) then
55  return
56 end if
57 
58 ! This is the inital guess of SA using a purpose-built polynomial in CT and p
59 sa = gsw_sa_freezing_estimate(p,saturation_fraction,t=t)
60 if (sa .lt. -sa_cut_off) then
62  return
63 end if
64 
65 ! Form the first estimate of tfreezing_SA, the derivative of CT_freezing
66 ! with respect to SA at fixed p.
67 sa = max(sa,0.0_r8)
68 call gsw_t_freezing_first_derivatives(sa,p,saturation_fraction, &
69  tfreezing_sa=tfreezing_sa)
70 
71 ! For -SA_cut_off < SA < SA_cut_off, replace the above estimate of SA
72 ! with one based on (t_freezing_zero_SA - t).
73 if (abs(sa) .lt. sa_cut_off) sa = (t - t_freezing_zero_sa)/tfreezing_sa
74 
75 !---------------------------------------------------------------------------
76 ! Begin the modified Newton-Raphson method to find the root of
77 ! f = (t_freezing - t) = 0 for SA.
78 !---------------------------------------------------------------------------
79 do i_iter = 1, number_of_iterations
80  sa_old = sa
81  f = gsw_t_freezing_exact(sa_old,p,saturation_fraction) - t
82  sa = sa_old - f/tfreezing_sa
83  sa_mean = 0.5_r8*(sa + sa_old)
84  call gsw_t_freezing_first_derivatives(sa_mean,p,saturation_fraction, &
85  tfreezing_sa=tfreezing_sa)
86  sa = sa_old - f/tfreezing_sa
87 end do
88 
89 if (gsw_sa_p_inrange(sa,p)) then
91 else
93 end if
94 
95 return
96 end function
97 
98 !---------------------------------------------------------------------------
real(r8), parameter, public gsw_error_limit
#define max(a, b)
Definition: mosaic_util.h:33
elemental real(r8) function gsw_sa_freezing_from_t(t, p, saturation_fraction)
elemental real(r8) function, public gsw_error_code(err_num, func_name, error_code)