comslope_mod.F90
快速理解
它做什么: 次网格坡面参数化的共享状态模块(Lange et al. 2023);保存坡面统计分布、坡度边界和天空可视比例。
基本过程: 持有 nslope/iflat/def_slope/def_slope_mean/sky_slope/subslope_dist → 提供初始化/释放/网格平均计算。
关键结果: 为坡面微物理/辐射提供分区计算的共享变量入口。
路径
LMDZ.MARS\libf\phymars\comslope_mod.F90
所属目录/模块
libf/phymars
文件定位
次网格坡面(subgrid slope)参数化共享状态模块。定义坡面统计分布、坡度边界、天空可视比例等共享变量,并提供初始化、释放和网格平均计算子程序。用于 Mars PCM 的次网格坡面微气候参数化方案。
定义的符号
| 符号 | 类型 | 行号 | 作用 |
|---|---|---|---|
comslope_mod |
module | 1 | 次网格坡面参数化共享模块 |
nslope |
module variable | 15 | 坡面数量(统计 bin 数) |
iflat |
module variable | 16 | 平坦坡面对应的 islope 索引 |
def_slope |
module variable | 17 | 坡面统计边界数组(度) |
def_slope_mean |
module variable | 18 | 每个 bin 的平均坡度(度) |
sky_slope |
module variable | 19 | 每个坡面可见天空比例 |
subslope_dist |
module variable | 20 | 坡面在网格中的分布比例 |
major_slope |
module variable | 21 | 占据网格大部分面积的次坡面索引 |
ini_comslope_h |
subroutine | 28 | 初始化分配坡面数组 |
end_comslope_h |
subroutine | 45 | 释放坡面数组 |
compute_meshgridavg |
subroutine | 59 | 计算坡面属性的网格平均值 |
依赖的模块
| use 模块 | only 列表 | 用途 | 待确认 |
|---|---|---|---|
comcstfi_h |
pi |
圆周率常数(角度转弧度) | — |
调用的关键例程
| 被调用例程 | 所在模块/文件 | 调用位置 | 作用 |
|---|---|---|---|
| (无外部调用) | — | — | 本模块为共享状态容器,不调用外部例程 |
输入
| 输入 | 来源 | 类型/维度 | 单位 | 含义 |
|---|---|---|---|---|
ngrid |
调用方 | integer | — | 物理网格点数量 |
nslope_in |
调用方 | integer | — | 坡面 bin 数量(初始化参数) |
nq |
调用方 | integer | — | tracer 数量 |
albedo_slope(ngrid,2,nslope) |
调用方 | real array | — | 各坡面的反照率(2 波段) |
emis_slope(ngrid,nslope) |
调用方 | real array | — | 各坡面的发射率 |
tsurf_slope(ngrid,nslope) |
调用方 | real array | K | 各坡面的地表温度 |
qsurf_slope(ngrid,nq,nslope) |
调用方 | real array | kg/m² (sloped) | 各坡面的地表 tracer 含量 |
输出
| 输出 | 去向 | 类型/维度 | 单位 | 含义 |
|---|---|---|---|---|
albedo_meshavg(ngrid,2) |
调用方 | real array | — | 网格平均反照率 |
emis_meshavg(ngrid) |
调用方 | real array | — | 网格平均发射率 |
tsurf_meshavg(ngrid) |
调用方 | real array | K | 网格平均地表温度 |
qsurf_meshavg(ngrid,nq) |
调用方 | real array | kg/m² (flat) | 网格平均地表 tracer 含量 |
共享状态与副作用
- Module 变量(全部
save+!$OMP THREADPRIVATE):nslope— 坡面 bin 数量iflat— 平坦坡面索引def_slope(nslope+1)— 坡面边界数组(度)def_slope_mean(nslope)— 每个 bin 的平均坡度(度)sky_slope(nslope)— 每个坡面可见天空比例subslope_dist(ngrid,nslope)— 坡面在网格中的分布比例major_slope(ngrid)— 占据网格大部分的次坡面索引
- OpenMP: 所有共享变量使用
THREADPRIVATE,每个线程独立副本 - 内存管理:
ini_comslope_h分配,end_comslope_h释放
核心逻辑
初始化(
ini_comslope_h,行 28-41):- 接收
ngrid和nslope_in - 分配 5 个数组:
def_slope、def_slope_mean、sky_slope、subslope_dist、major_slope
- 接收
释放(
end_comslope_h,行 45-55):- 检查每个数组是否已分配,若已分配则释放
网格平均计算(
compute_meshgridavg,行 59-105):- 快速路径(行 84-88):若
nslope==1,直接赋值(无次网格) - 一般路径(行 89-103):
- 反照率:
albedo_meshavg += albedo_slope * subslope_dist - tracer:
qsurf_meshavg += qsurf_slope * subslope_dist / cos(slope_angle)(坡面→水平投影转换) - 发射率:
emis_meshavg += emis_slope * subslope_dist - 温度:
tsurf_meshavg += emis_slope * tsurf_slope^4 * subslope_dist(Stefan-Boltzmann 加权) - 最终温度:
tsurf_meshavg = (tsurf_meshavg / emis_meshavg)^0.25
- 反照率:
- 快速路径(行 84-88):若
伪代码
! 初始化
SUBROUTINE ini_comslope_h(ngrid, nslope_in)
分配 def_slope(nslope_in+1)
分配 def_slope_mean(nslope_in)
分配 sky_slope(nslope_in)
分配 subslope_dist(ngrid, nslope_in)
分配 major_slope(ngrid)
! 释放
SUBROUTINE end_comslope_h
释放所有已分配数组
! 网格平均
SUBROUTINE compute_meshgridavg(ngrid, nq, albedo_slope, emis_slope, tsurf_slope, qsurf_slope, ...)
IF nslope == 1 THEN
直接赋值(无次网格)
ELSE
DO ig = 1, ngrid
DO islope = 1, nslope
albedo_meshavg += albedo_slope * subslope_dist
qsurf_meshavg += qsurf_slope * subslope_dist / cos(slope_angle) ! 坡面→水平投影
emis_meshavg += emis_slope * subslope_dist
tsurf_meshavg += emis_slope * tsurf_slope^4 * subslope_dist ! Stefan-Boltzmann 加权
END DO
tsurf_meshavg = (tsurf_meshavg / emis_meshavg)^0.25 ! 反推平均温度
END DO
END IF
参与的主题流程
| 主题 | 参与方式 |
|---|---|
| 水循环 | 坡面微气候影响地表水冰交换(vdifc 调用) |
| CO2 循环 | 坡面温度影响 CO2 凝结/升华(co2condens 调用) |
| 辐射计算 | 坡面反照率和发射率影响辐射收支 |
写法特点
- OpenMP 并行: 所有共享变量使用
!$OMP THREADPRIVATE,每个线程独立副本 - SAVE 属性: 所有 module 变量使用
save,保持调用间状态 - 条件分配:
ini_comslope_h负责分配,end_comslope_h负责释放 - 快速路径:
nslope==1时跳过加权平均,直接赋值 - 角度投影: tracer 使用
cos(slope_angle)转换坡面→水平投影 - Stefan-Boltzmann 加权: 温度平均使用
T^4加权而非直接平均
复现要点
def_slope长度为nslope+1(边界),def_slope_mean长度为nslope(中心值)qsurf_slope单位为kg/m² sloped,输出qsurf_meshavg单位为kg/m² flat(需除以cos(slope))- 温度平均使用 Stefan-Boltzmann 加权(
T^4),不是算术平均 - 所有变量为 OpenMP THREADPRIVATE,多线程时每个线程独立
已确认初始化与使用链
| 文件 | 位置 | 作用 |
|---|---|---|
phys_state_var_init_mod.F90 |
行 64, 191-193 | 使用 ini_comslope_h / end_comslope_h,按 ngrid,nslope 分配 comslope_mod 数组 |
physiq_mod.F |
行 131-134, 628-634 | physiq 引入坡面共享变量,并把 def_slope、def_slope_mean、subslope_dist 传给 phyetat0 读取初始状态 |
phyetat0_mod.F90 |
行 153-185 | 从 start 文件读取 def_slope 和 subslope_dist;无 start 文件且 nslope==1 时设默认值 |
phyetat0_mod.F90 |
行 192-203 | 用相邻边界平均得到 def_slope_mean,并逐网格归一化 subslope_dist |
phyetat0_mod.F90 |
行 206-215 | 选出每个网格占比最大的 major_slope |
physiq_mod.F |
行 636-649 | 用 def_slope_mean 计算 sky_slope,并选出绝对坡度最小的 iflat |
physiq_mod.F |
行 857, 1617, 2567 | 调用 compute_meshgridavg 把坡面态汇总到网格平均态 |
physiq_mod.F |
行 1199-1282 | 坡面辐射修正使用 def_slope_mean 和 sky_slope |
vdifc_mod.F |
行 286-287, 437-454, 653, 684, 783 | 使用 major_slope 选择主坡面温度、地表 tracer 与交换系数 |
待确认
def_slope与subslope_dist写入 start 文件的上游生成路径(可能由newstart/地形预处理流程产生)- Lange et al. (2023) 论文是否已发表
相关页面
- 水循环主题页:water-cycle
- vdifc 水汽地表交换段:vdifc-water-surface-exchange
- CO2 循环主题页:co2-cycle
- slope_mod.md:坡面辐射几何/参数化。
- phyetat0_mod.md:物理初始状态读取。