!> author: Sam Hatfield, Fred Kucharski, Franco Molteni ! date: 01/05/2019 ! For setting all time-dependent forcing fields. module forcing use types, only : p implicit none private public set_forcing contains !> Compute forcing fields for the current date and correction terms for ! horizontal diffusion subroutine set_forcing(state, imode, model_datetime, tyear) use physical_constants, only : refrh1 use params use physical_constants, only : rgas use surface_fluxes, only : set_orog_land_sfc_drag use model_control, only : Datetime_t use land_model, only : snow_depth2cover use mod_radcon, only : albsea, albice, albsn use shortwave_radiation, only : get_zonal_average_fields use longwave_radiation, only : radset use humidity, only : get_qsat use model_state, only : ModelState_t type(ModelState_t), intent(inout) :: state integer, intent(in) :: imode !! Mode -> 0 = initialization step, 1 = daily update type(Datetime_t), intent(in) :: model_datetime real(p), intent(in) :: tyear !! The fraction of the current year elapsed real(p), dimension(ix, il) :: corh, tsfc, tref, psfc, qsfc, qref real(p) :: gamlat(il) real(p) :: del_co2, pexp integer :: i, j, iyear_ref ! time variables for interpolation are set by newdate ! 1. time-independent parts of physical parametrizations if (imode == 0) then call radset(state%fband) call set_orog_land_sfc_drag(state%phis0, state%forog) state%ablco2_ref = state%air_absortivity_co2 end if ! 2. daily-mean radiative forcing ! incoming solar radiation call get_zonal_average_fields(state, tyear) ! total surface albedo do i = 1, ix do j = 1, il state%snowc(i, j) = min(1.0, state%snow_depth(i, j) / snow_depth2cover) state%alb_land(i, j) = state%alb0(i, j) + state%snowc(i, j) * (albsn - state%alb0(i, j)) state%alb_sea(i, j) = albsea + state%sice_am(i, j) * (albice - albsea) state%alb_surface(i, j) = state%alb_sea(i, j) & + state%fmask_land(i, j) * (state%alb_land(i, j) - state%alb_sea(i, j)) end do end do ! linear trend of co2 absorptivity (del_co2: rate of change per year) iyear_ref = 1950 del_co2 = 0.005 ! del_co2 = 0.0033 if (state%increase_co2) then state%air_absortivity_co2 = state%ablco2_ref * exp(del_co2 * (model_datetime%year + tyear - iyear_ref)) end if ! 3. temperature correction term for horizontal diffusion call setgam(gamlat) do j = 1, il do i = 1, ix corh(i, j) = gamlat(j) * state%phis0(i, j) end do end do state%mod_implicit%tcorh = state%mod_spectral%grid2spec(corh) ! 4. humidity correction term for horizontal diffusion do j = 1, il pexp = 1. / (rgas * gamlat(j)) do i = 1, ix tsfc(i, j) = state%fmask_land(i, j) * state%land_temp(i, j) + state%fmask_sea(i, j) * state%sst_am(i, j) tref(i, j) = tsfc(i, j) + corh(i, j) psfc(i, j) = (tsfc(i, j) / tref(i, j))**pexp end do end do qref = get_qsat(tref, psfc / psfc, -1.0_p) qsfc = get_qsat(tsfc, psfc, 1.0_p) corh = refrh1 * (qref - qsfc) state%mod_implicit%qcorh = state%mod_spectral%grid2spec(corh) end subroutine !> Compute reference lapse rate as a function of latitude and date subroutine setgam(gamlat) use physical_constants, only : gamma use params use physical_constants, only : grav real(p), intent(inout) :: gamlat(il) !! The reference lapse rate integer :: j gamlat(1) = gamma / (1000. * grav) do j = 2, il gamlat(j) = gamlat(1) end do end subroutine end module