//! ALI 频率相关计算 - 变体 1。 //! //! 重构自 TLUSTY `alifr1.f` //! //! 计算流体静力学和辐射平衡量 - ALI 点的总加热和冷却率对 //! 温度、电子密度和占据数的导数。 //! 这是一致三对角算子的变体。 //! //! ## 实现状态 //! 完整实现。包含以下代码路径: //! - ILMCOR == 3, ILASCT == 0(标准路径) //! - ILMCOR == 3, ILASCT != 0 //! - ILMCOR != 3, ILASCT == 0 //! - ILMCOR != 3, ILASCT != 0 //! - 完整的边界条件处理 (IBC = 0, 1, 2, 3+) //! //! 当 IFALI > 5 时,返回 `true`,调用者应调用 `alifr3`。 use crate::state::alipar::FixAlp; use crate::state::constants::{UN, TWO, HALF}; /// ALIFR1 输入参数 pub struct Alifr1Params { /// 频率索引 (1-indexed) pub ij: usize, /// 深度点数 pub nd: usize, /// 线性化能级数 pub nlvexp: usize, /// ALI 模式 pub ifali: i32, /// 辐射导数模式 pub irder: i32, /// ILMCOR 参数 pub ilmcor: i32, /// ILASCT 参数 pub ilasct: i32, /// 边界条件类型 pub ibc: i32, /// 是否为盘模型 pub idisk: i32, /// IFALIH 参数 pub ifalih: i32, } /// ALIFR1 需要的模型状态输入 pub struct Alifr1ModelState<'a> { // 深度相关 (MDEPTH) pub elec: &'a [f64], pub dens: &'a [f64], pub densi: &'a [f64], pub densim: &'a [f64], pub dens1: &'a [f64], pub dm: &'a [f64], pub deldmz: &'a [f64], pub elscat: &'a [f64], pub absot: &'a [f64], pub hkt21: &'a [f64], pub xkfb: &'a [f64], pub xkf1: &'a [f64], // 辐射相关 (MDEPTH) pub rad1: &'a [f64], pub fak1: &'a [f64], // 频率相关 pub freq: &'a [f64], pub hextrd: &'a [f64], pub sigec: &'a [f64], pub sige: f64, pub extrad: &'a [f64], pub fh: &'a [f64], pub w: &'a [f64], /// 表面辐射通量 Q0 (MFREQ) pub q0: &'a [f64], // 跳过标志 (MDEPTH × MFREQ) pub lskip: &'a [Vec], // 平衡相关 pub reint: &'a [f64], pub redif: &'a [f64], // 输出累积变量 pub fprd: &'a mut [f64], pub flfix: &'a mut [f64], pub flrd: &'a mut [f64], pub fcooli: &'a mut [f64], pub heit: &'a mut [f64], pub hein: &'a mut [f64], pub heim: &'a mut [f64], pub heitm: &'a mut [f64], pub heinm: &'a mut [f64], pub heimm: &'a mut [f64], pub heip: &'a mut [Vec], pub heipm: &'a mut [Vec], pub redt: &'a mut [f64], pub redn: &'a mut [f64], pub redm: &'a mut [f64], pub redx: &'a mut [f64], pub redtm: &'a mut [f64], pub rednm: &'a mut [f64], pub redmm: &'a mut [f64], pub redxm: &'a mut [f64], pub redp: &'a mut [Vec], pub redpm: &'a mut [Vec], pub rein: &'a mut [f64], pub reit: &'a mut [f64], pub reim: &'a mut [f64], pub reip: &'a mut [Vec], } /// ALIFR1 需要的辐射/不透明度状态 pub struct Alifr1RadState<'a> { /// 权重因子 (MFREQ) pub wc: &'a [f64], /// 当前频率发射系数 (MDEPTH) pub emis1: &'a [f64], /// 当前频率吸收系数 (MDEPTH) pub abso1: &'a [f64], /// 当前频率散射系数 (MDEPTH) pub scat1: &'a [f64], /// 发射系数 T 导数 (MDEPTH) pub demt1: &'a [f64], /// 发射系数 N 导数 (MDEPTH) pub demn1: &'a [f64], /// 发射系数 M 导数 (MDEPTH) pub demm1: &'a [f64], /// 吸收系数 T 导数 (MDEPTH) pub dabt1: &'a [f64], /// 吸收系数 N 导数 (MDEPTH) pub dabn1: &'a [f64], /// 吸收系数 M 导数 (MDEPTH) pub dabm1: &'a [f64], /// 发射系数能级导数 (MLVEXP × MDEPTH) pub demp1: &'a [Vec], /// 吸收系数能级导数 (MLVEXP × MDEPTH) pub dabp1: &'a [Vec], } /// 计算 ALI 频率相关量 - 变体 1。 /// /// # 参数 /// /// * `params` - 输入参数 /// * `fixalp` - ALI 固定参数 /// * `model` - 模型状态 /// * `rad` - 辐射状态 /// /// # 返回值 /// /// 返回 `true` 表示调用者应该调用 `alifr3`(当 IFALI > 5 时)。 /// 返回 `false` 表示处理已完成或无需进一步操作。 /// /// # Fortran 索引说明 /// /// - IJ 是频率索引 (1-indexed) /// - ID 是深度索引 (1-indexed) /// - II 是能级索引 (1-indexed) /// /// # 实现状态 /// /// 完整实现: /// - IFALI <= 1 时直接返回 /// - IFALI > 5 时返回 true(调用者应调用 alifr3) /// - ILMCOR == 3 且 ILASCT == 0 的标准路径 /// - ILMCOR == 3 且 ILASCT != 0 的路径 /// - ILMCOR != 3 的路径 /// - 完整的深度循环和边界条件处理(IBC = 0, 1, 2, 3+) #[allow(clippy::too_many_arguments)] pub fn alifr1( params: &Alifr1Params, fixalp: &mut FixAlp, model: &mut Alifr1ModelState, rad: &Alifr1RadState, ) -> bool { // 如果 IFALI <= 1,直接返回 if params.ifali <= 1 { return false; } // 如果 IFALI > 5,返回 true 指示调用者应该调用 ALIFR3 // 注意:由于 Rust 借用限制,ALIFR3 需要由调用者直接调用 if params.ifali > 5 { return true; } let ij = params.ij; let nd = params.nd; let nlvexp = params.nlvexp; // 获取权重因子 let ww = rad.wc[ij - 1]; // 常量 let t23 = TWO / 3.0; // 根据 ILMCOR 值选择不同的处理路径 if params.ilmcor == 3 { // ================================================================ // ILMCOR == 3 的处理(标准情况) // ================================================================ process_standard_path(params, fixalp, model, rad, ij, nd, nlvexp, ww, t23); return false; } // ================================================================ // ILMCOR != 3 的处理(非标准情况) // ILASCT == 0 的分支 // ================================================================ if params.ilasct == 0 { process_ilasct_zero(params, fixalp, model, rad, ij, nd, nlvexp, ww); return false; } // ================================================================ // ILASCT != 0 的处理 // ================================================================ process_ilasct_nonzero(params, fixalp, model, rad, ij, nd, nlvexp, ww); false } /// 处理标准路径 (ILMCOR == 3, ILASCT == 0) #[allow(clippy::too_many_arguments)] fn process_standard_path( params: &Alifr1Params, fixalp: &mut FixAlp, model: &mut Alifr1ModelState, rad: &Alifr1RadState, ij: usize, nd: usize, nlvexp: usize, ww: f64, t23: f64, ) { // 初始化中间变量 let mut dsft1m: f64 = 0.0; let mut dsfn1m: f64 = 0.0; let mut dsfm1m: f64 = 0.0; let mut dsfp1m = vec![0.0; nlvexp]; // 1. 第一个深度点 (ID=1) let id = 1; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 基本辅助量 - 源函数的导数 let emisiv = if rad.emis1[id_idx] < 1e-35 { 1e35 } else { UN / rad.emis1[id_idx] }; let abst = UN / rad.abso1[id_idx]; let mut s0 = rad.emis1[id_idx] * abst; // 改进边界条件的贡献 let dt = (rad.abso1[id_idx] / model.dens[id_idx] + rad.abso1[id] / model.dens[id]) * (model.dm[id] - model.dm[id_idx]) * HALF; let sa = s0 * (UN + 4.0 / dt * model.q0[ij - 1]); s0 = s0 * (UN + TWO / dt * model.q0[ij - 1]); let sc = rad.scat1[id_idx]; let sct = sc * abst; let corr = UN / (UN - fixalp.ali1[id_idx] * sct); let dsft1 = corr * (s0 * rad.demt1[id_idx] * emisiv - s0 * rad.dabt1[id_idx] * abst); let dsfn1 = corr * (s0 * rad.demn1[id_idx] * emisiv - s0 * rad.dabn1[id_idx] * abst); let dsfm1 = corr * (s0 * rad.demm1[id_idx] * emisiv - s0 * rad.dabm1[id_idx] * abst); let mut dsfp1 = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1[ii] = corr * (s0 * rad.demp1[ii][id_idx] * emisiv - sa * rad.dabp1[ii][id_idx] * abst); } // ID+1 的值 let idp_idx = id; let emisip = if rad.emis1[idp_idx] < 1e-35 { 1e35 } else { UN / rad.emis1[idp_idx] }; let abstp = UN / rad.abso1[idp_idx]; let s0p = rad.emis1[idp_idx] * abstp; let scp = rad.scat1[idp_idx]; let sctp = scp * abstp; let corrp = UN / (UN - fixalp.ali1[idp_idx] * sctp); let mut dsft1p = corrp * (s0p * rad.demt1[idp_idx] * emisip - s0p * rad.dabt1[idp_idx] * abstp); let mut dsfn1p = corrp * (s0p * rad.demn1[idp_idx] * emisip - s0p * rad.dabn1[idp_idx] * abstp); let mut dsfm1p = corrp * (s0p * rad.demm1[idp_idx] * emisip - s0p * rad.dabm1[idp_idx] * abstp); let mut dsfp1p = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p[ii] = corrp * (s0p * rad.demp1[ii][idp_idx] * emisip - s0p * rad.dabp1[ii][idp_idx] * abstp); } // 更新 DSFDT, DSFDN, DSFDM 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1 * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1 * fixalp.ali1[id_idx]; fixalp.dsfdm[id_idx] = dsfm1 * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡量 let wf = ww * model.fh[ij - 1]; if lnskip { model.fprd[id_idx] += wf * rad.abso1[id_idx] * model.rad1[id_idx] - ww * model.hextrd[ij - 1] * rad.abso1[id_idx]; let e0 = wf * model.rad1[id_idx]; let d0 = wf * rad.abso1[id_idx] * fixalp.ali1[id_idx]; model.heit[id_idx] += d0 * dsft1 + e0 * rad.dabt1[id_idx]; model.hein[id_idx] += d0 * dsfn1 + e0 * rad.dabn1[id_idx]; model.heim[id_idx] += d0 * dsfm1 + e0 * rad.dabm1[id_idx]; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0 * dsfp1[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 辐射平衡微分方程部分 model.flfix[id_idx] += wf * model.rad1[id_idx] - ww * model.hextrd[ij - 1]; model.flrd[id_idx] += model.w[ij - 1] * model.fh[ij - 1] * model.rad1[id_idx] - model.w[ij - 1] * HALF * model.extrad[ij - 1]; if model.redif[id_idx] > 0.0 { let wf = wf * fixalp.ali1[id_idx]; model.redt[id_idx] += wf * dsft1; model.redn[id_idx] += wf * dsfn1; model.redm[id_idx] += wf * dsfm1; for ii in 0..nlvexp { model.redp[ii][id_idx] += wf * dsfp1[ii]; } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let d0 = abst_true * fixalp.ali1[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); model.reit[id_idx] += ww * (d0 * dsft1 + model.rad1[id_idx] * rad.dabt1[id_idx] - rad.demt1[id_idx]); model.rein[id_idx] += ww * (d0 * dsfn1 + model.rad1[id_idx] * (rad.dabn1[id_idx] - model.sigec[ij - 1]) - rad.demn1[id_idx]); model.reim[id_idx] += ww * (d0 * dsfm1 + model.rad1[id_idx] * rad.dabm1[id_idx] - rad.demm1[id_idx]); for ii in 0..nlvexp { model.reip[ii][id_idx] += ww * (d0 * dsfp1[ii] + model.rad1[id_idx] * rad.dabp1[ii][id_idx] - rad.demp1[ii][id_idx]); } } // 2. 深度循环 (ID = 2 to ND-1) for id in 2..nd { let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前一个点的值 dsft1m = dsft1; dsfn1m = dsfn1; dsfm1m = dsfm1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } // 更新当前点为上一个点的 ID+1 值 let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfm1_curr = dsfm1p; let dsfp1_curr = dsfp1p.clone(); // 计算 ID+1 的值 let idp_idx = id; let emisip_new = if rad.emis1[idp_idx] < 1e-35 { 1e35 } else { UN / rad.emis1[idp_idx] }; let abstp_new = UN / rad.abso1[idp_idx]; let s0p_new = rad.emis1[idp_idx] * abstp_new; let scp_new = rad.scat1[idp_idx]; let sctp_new = scp_new * abstp_new; let corrp_new = UN / (UN - fixalp.ali1[idp_idx] * sctp_new); dsft1p = corrp_new * (s0p_new * rad.demt1[idp_idx] * emisip_new - s0p_new * rad.dabt1[idp_idx] * abstp_new); dsfn1p = corrp_new * (s0p_new * rad.demn1[idp_idx] * emisip_new - s0p_new * rad.dabn1[idp_idx] * abstp_new); dsfm1p = corrp_new * (s0p_new * rad.demm1[idp_idx] * emisip_new - s0p_new * rad.dabm1[idp_idx] * abstp_new); dsfp1p = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p[ii] = corrp_new * (s0p_new * rad.demp1[ii][idp_idx] * emisip_new - s0p_new * rad.dabp1[ii][idp_idx] * abstp_new); } // 更新 DSFDT, DSFDN, DSFDM 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_curr * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; fixalp.dsfdm[id_idx] = dsfm1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_curr; model.hein[id_idx] += d0_new * dsfn1_curr; model.heim[id_idx] += d0_new * dsfm1_curr; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; model.heimm[id_idx] += e0 * dsfm1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_curr[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; model.flrd[id_idx] += model.w[ij - 1] * fl; if model.redif[id_idx] > 0.0 { if params.ifalih == 0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_curr - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_curr - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; model.redm[id_idx] += d0_new * dsfm1_curr - e0_new * rad.dabm1[id_idx]; model.redmm[id_idx] += d0m * dsfm1m - e0m * rad.dabm1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_curr[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } } else { let d0 = ww * fixalp.alih1[id_idx]; model.redt[id_idx] += d0 * dsft1_curr; model.redn[id_idx] += d0 * dsfn1_curr; model.redm[id_idx] += d0 * dsfm1_curr; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0 * dsfp1_curr[ii]; } } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let d0 = abst_true * fixalp.ali1[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); model.rein[id_idx] += ww * (d0 * dsfn1_curr + model.rad1[id_idx] * (rad.dabn1[id_idx] - model.sigec[ij - 1]) - rad.demn1[id_idx]); model.reit[id_idx] += ww * (d0 * dsft1_curr + model.rad1[id_idx] * rad.dabt1[id_idx] - rad.demt1[id_idx]); model.reim[id_idx] += ww * (d0 * dsfm1_curr + model.rad1[id_idx] * rad.dabm1[id_idx] - rad.demm1[id_idx]); for ii in 0..nlvexp { model.reip[ii][id_idx] += ww * (d0 * dsfp1_curr[ii] + model.rad1[id_idx] * rad.dabp1[ii][id_idx] - rad.demp1[ii][id_idx]); } } } // 3. 最深点 ID=ND let id = nd; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前一个点的值 let dsftmm = dsft1m; let dsfnmm = dsfn1m; let dsfmmm = dsfm1m; let mut dsfpmm = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfpmm[ii] = dsfp1m[ii]; } // 更新当前点为上一个点的 ID+1 值 dsft1m = dsft1; dsfn1m = dsfn1; dsfm1m = dsfm1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfm1_curr = dsfm1p; let dsfp1_curr = dsfp1p.clone(); // 初始化 ID-1 的导数(用于边界条件) let mut dsft1d: f64 = 0.0; let mut dsfn1d: f64 = 0.0; let mut dsfm1d: f64 = 0.0; let mut dsfp1d = vec![0.0; nlvexp]; // 初始化 DBDT 和 E0(用于改进边界条件的积分方程) // 这些变量在边界条件块中计算,在积分方程块中使用 let mut dbdt: f64 = 0.0; let mut e0: f64 = 0.0; // 改进的下边界条件 if params.ibc > 0 && params.idisk == 0 { let dt = UN / (model.deldmz[id_idx - 1] * (model.absot[id_idx] + model.absot[id_idx - 1])); let plad = model.xkfb[id_idx] / model.xkf1[id_idx]; dbdt = plad / model.xkf1[id_idx] * model.hkt21[id_idx] * model.freq[ij - 1] * dt; if params.ibc == 1 { // 简单边界条件 fixalp.dsfdt[id_idx] = (dsft1_curr + dbdt) * fixalp.ali1[id_idx]; } else if params.ibc >= 2 { // 改进的边界条件 let plam = model.xkfb[id_idx - 1] / model.xkf1[id_idx - 1]; let tau23 = t23 * dt; let tau43 = 4.0 / 3.0 * dt; let d0 = (plad * (UN + tau43) - tau43 * plam * dt) * dt * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx]; e0 = d0 * rhd; let dsft1_new = dsft1_curr + dbdt * (UN + tau23) - e0 * rad.dabt1[id_idx]; let dsfn1_new = dsfn1_curr - e0 * (rad.dabn1[id_idx] + rad.abso1[id_idx] * model.densim[id_idx]); let dsfm1_new = dsfm1_curr - e0 * rad.dabm1[id_idx]; let mut dsfp1_new = dsfp1_curr.clone(); for ii in 0..nlvexp { dsfp1_new[ii] = dsfp1_curr[ii] - e0 * rad.dabp1[ii][id_idx]; } if params.ibc >= 3 { let dbdtm = plam / model.xkf1[id_idx - 1] * model.hkt21[id_idx - 1] * model.freq[ij - 1] * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx - 1]; let e0 = d0 * rhd; dsft1d = -dbdtm * dt * t23 - e0 * rad.dabt1[id_idx - 1]; dsfn1d = -e0 * (rad.dabn1[id_idx - 1] + rad.abso1[id_idx - 1] * model.densim[id_idx - 1]); dsfm1d = -e0 * rad.dabm1[id_idx - 1]; for ii in 0..nlvexp { dsfp1d[ii] = -e0 * rad.dabp1[ii][id_idx - 1]; } } // 更新 DSFDT, DSFDN, DSFDM if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_new * fixalp.ali1[id_idx]; fixalp.dsfdm[id_idx] = dsfm1_new * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_new[ii] * fixalp.ali1[id_idx]; } } } else { // IBC == 1 的情况 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = (dsft1_curr + dbdt) * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; fixalp.dsfdm[id_idx] = dsfm1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } } else { // 标准边界条件 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_curr * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; fixalp.dsfdm[id_idx] = dsfm1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_curr; model.hein[id_idx] += d0_new * dsfn1_curr; model.heim[id_idx] += d0_new * dsfm1_curr; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; model.heimm[id_idx] += e0 * dsfm1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_curr[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } if params.ibc >= 3 { model.heitm[id_idx] -= d0_new * dsft1d; model.heinm[id_idx] -= d0_new * dsfn1d; model.heimm[id_idx] -= d0_new * dsfm1d; for ii in 0..nlvexp { model.heipm[ii][id_idx] -= d0_new * dsfp1d[ii]; } } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; model.flrd[id_idx] += model.w[ij - 1] * fl; if model.redif[id_idx] > 0.0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_curr - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_curr - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; model.redm[id_idx] += d0_new * dsfm1_curr - e0_new * rad.dabm1[id_idx]; model.redmm[id_idx] += d0m * dsfm1m - e0m * rad.dabm1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_curr[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } if params.ibc >= 3 { model.redtm[id_idx] += d0_new * dsft1d; model.rednm[id_idx] += d0_new * dsfn1d; model.redmm[id_idx] += d0_new * dsfm1d; for ii in 0..nlvexp { model.redpm[ii][id_idx] += d0_new * dsfp1d[ii]; } } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let d0 = abst_true * fixalp.ali1[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); model.rein[id_idx] += ww * (d0 * dsfn1_curr + model.rad1[id_idx] * (rad.dabn1[id_idx] - model.sigec[ij - 1]) - rad.demn1[id_idx]); model.reim[id_idx] += ww * (d0 * dsfm1_curr + model.rad1[id_idx] * rad.dabm1[id_idx] - rad.demm1[id_idx]); for ii in 0..nlvexp { model.reip[ii][id_idx] += ww * (d0 * dsfp1_curr[ii] + model.rad1[id_idx] * rad.dabp1[ii][id_idx] - rad.demp1[ii][id_idx]); } if params.ibc == 0 { model.reit[id_idx] += ww * (d0 * dsft1_curr + model.rad1[id_idx] * rad.dabt1[id_idx] - rad.demt1[id_idx]); } else { // 改进的边界条件下的积分方程 // Fortran: REIT(ID)=REIT(ID)+WW*(D0*(DSFT1-DBDT)+E0*DABT1(ID)+ // * RAD1(ID)*DABT1(ID)-DEMT1(ID)+ // * ALI1(ID)/ABST*DBDT) model.reit[id_idx] += ww * (d0 * (dsft1_curr - dbdt) + e0 * rad.dabt1[id_idx] + model.rad1[id_idx] * rad.dabt1[id_idx] - rad.demt1[id_idx] + fixalp.ali1[id_idx] / abst_true * dbdt); } } } /// 处理 ILASCT == 0 但 ILMCOR != 3 的情况 /// 这个路径与标准路径的主要区别是源函数导数的计算方式 #[allow(clippy::too_many_arguments)] fn process_ilasct_zero( params: &Alifr1Params, fixalp: &mut FixAlp, model: &mut Alifr1ModelState, rad: &Alifr1RadState, ij: usize, nd: usize, nlvexp: usize, ww: f64, ) { // 常量 let t23 = TWO / 3.0; // 初始化中间变量 let mut dsft1m: f64 = 0.0; let mut dsfn1m: f64 = 0.0; let mut dsfp1m = vec![0.0; nlvexp]; // 1. 第一个深度点 (ID=1) let id = 1; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 基本辅助量 - 源函数的导数(非标准方式) let emisiv = UN / rad.emis1[id_idx]; let abst = UN / (rad.abso1[id_idx] - model.elscat[id_idx]); let s0 = rad.emis1[id_idx] * abst; let dsfn1 = s0 * (rad.demn1[id_idx] * emisiv - (rad.dabn1[id_idx] - model.sigec[ij - 1]) * abst); let dsft1 = s0 * (rad.demt1[id_idx] * emisiv - rad.dabt1[id_idx] * abst); let mut dsfp1 = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1[ii] = s0 * (rad.demp1[ii][id_idx] * emisiv - rad.dabp1[ii][id_idx] * abst); } // ID+1 的值 let idp_idx = id; let emisip = UN / rad.emis1[idp_idx]; let abstp = UN / (rad.abso1[idp_idx] - model.elscat[idp_idx]); let s0p = rad.emis1[idp_idx] * abstp; let mut dsfn1p = s0p * (rad.demn1[idp_idx] * emisip - (rad.dabn1[idp_idx] - model.sigec[ij - 1]) * abstp); let mut dsft1p = s0p * (rad.demt1[idp_idx] * emisip - rad.dabt1[idp_idx] * abstp); let mut dsfp1p = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p[ii] = s0p * (rad.demp1[ii][idp_idx] * emisip - rad.dabp1[ii][idp_idx] * abstp); } // 更新 DSFDT, DSFDN 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1 * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1 * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡量 let wf = ww * model.fh[ij - 1]; if lnskip { model.fprd[id_idx] += wf * rad.abso1[id_idx] * model.rad1[id_idx] - ww * model.hextrd[ij - 1] * rad.abso1[id_idx]; let e0 = wf * model.rad1[id_idx]; let d0 = wf * rad.abso1[id_idx] * fixalp.ali1[id_idx]; model.heit[id_idx] += d0 * dsft1 + e0 * rad.dabt1[id_idx]; model.hein[id_idx] += d0 * dsfn1 + e0 * rad.dabn1[id_idx]; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0 * dsfp1[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 辐射平衡微分方程部分 model.flfix[id_idx] += wf * model.rad1[id_idx] - ww * model.hextrd[ij - 1]; model.flrd[id_idx] += model.w[ij - 1] * model.fh[ij - 1] * model.rad1[id_idx] - model.w[ij - 1] * HALF * model.extrad[ij - 1]; if model.redif[id_idx] > 0.0 { let wf = wf * fixalp.ali1[id_idx]; model.redt[id_idx] += wf * dsft1; model.redn[id_idx] += wf * dsfn1; for ii in 0..nlvexp { model.redp[ii][id_idx] += wf * dsfp1[ii]; } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let wwk = ww * abst_true; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); let d0 = ww * (fixalp.ali1[id_idx] - UN) * abst_true; let e0 = ww * (model.rad1[id_idx] - s0); model.rein[id_idx] += d0 * dsfn1 + e0 * (rad.dabn1[id_idx] - model.sigec[ij - 1]); model.reit[id_idx] += d0 * dsft1 + e0 * rad.dabt1[id_idx]; for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 2. 深度循环 (ID = 2 to ND-1) for id in 2..nd { let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前一个点的值 dsft1m = dsft1; dsfn1m = dsfn1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } // 更新当前点为上一个点的 ID+1 值 let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfp1_curr = dsfp1p.clone(); // 计算 ID+1 的值 let idp_idx = id; let emisip_new = UN / rad.emis1[idp_idx]; let abstp_new = UN / (rad.abso1[idp_idx] - model.elscat[idp_idx]); let s0p_new = rad.emis1[idp_idx] * abstp_new; let dsfn1p_new = s0p_new * (rad.demn1[idp_idx] * emisip_new - (rad.dabn1[idp_idx] - model.sigec[ij - 1]) * abstp_new); let dsft1p_new = s0p_new * (rad.demt1[idp_idx] * emisip_new - rad.dabt1[idp_idx] * abstp_new); let mut dsfp1p_new = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p_new[ii] = s0p_new * (rad.demp1[ii][idp_idx] * emisip_new - rad.dabp1[ii][idp_idx] * abstp_new); } dsft1p = dsft1p_new; dsfn1p = dsfn1p_new; dsfp1p = dsfp1p_new; // 更新 DSFDT, DSFDN 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_curr * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_curr; model.hein[id_idx] += d0_new * dsfn1_curr; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_curr[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; if model.redif[id_idx] > 0.0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_curr - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_curr - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_curr[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let wwk = ww * abst_true; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); let d0 = ww * (fixalp.ali1[id_idx] - UN) * abst_true; let e0 = ww * (model.rad1[id_idx] - s0); model.rein[id_idx] += d0 * dsfn1_curr + e0 * (rad.dabn1[id_idx] - model.sigec[ij - 1]); model.reit[id_idx] += d0 * dsft1_curr + e0 * rad.dabt1[id_idx]; for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1_curr[ii] + e0 * rad.dabp1[ii][id_idx]; } } } // 3. 最深点 ID=ND let id = nd; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前一个点的值 let _dsftmm = dsft1m; let _dsfnmm = dsfn1m; let mut _dsfpmm = vec![0.0; nlvexp]; for ii in 0..nlvexp { _dsfpmm[ii] = dsfp1m[ii]; } // 更新当前点为上一个点的 ID+1 值 dsft1m = dsft1; dsfn1m = dsfn1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } let s0_curr = s0p; let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfp1_curr = dsfp1p.clone(); // 初始化 ID-1 的导数(用于边界条件) let mut dsft1d: f64 = 0.0; let mut dsfn1d: f64 = 0.0; let mut dsfp1d = vec![0.0; nlvexp]; // 改进的下边界条件 let mut dbdt: f64 = 0.0; if params.ibc > 0 && params.idisk == 0 { let dt = UN / (model.deldmz[id_idx - 1] * (model.absot[id_idx] + model.absot[id_idx - 1])); let plad = model.xkfb[id_idx] / model.xkf1[id_idx]; dbdt = plad / model.xkf1[id_idx] * model.hkt21[id_idx] * model.freq[ij - 1] * dt; if params.ibc == 1 { // 简单边界条件 - DSFT1 = DSFT1 + DBDT let dsft1_new = dsft1_curr + dbdt; if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } else if params.ibc >= 2 { // 改进的边界条件 let plam = model.xkfb[id_idx - 1] / model.xkf1[id_idx - 1]; let tau23 = t23 * dt; let tau43 = 4.0 / 3.0 * dt; let d0_val = (plad * (UN + tau43) - tau43 * plam * dt) * dt * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx]; let e0 = d0_val * rhd; let dsft1_new = dsft1_curr + dbdt * (UN + tau23) - e0 * rad.dabt1[id_idx]; let dsfn1_new = dsfn1_curr - e0 * (rad.dabn1[id_idx] + rad.abso1[id_idx] * model.densim[id_idx]); let mut dsfp1_new = dsfp1_curr.clone(); for ii in 0..nlvexp { dsfp1_new[ii] = dsfp1_curr[ii] - e0 * rad.dabp1[ii][id_idx]; } if params.ibc >= 3 { let dbdtm = plam / model.xkf1[id_idx - 1] * model.hkt21[id_idx - 1] * model.freq[ij - 1] * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx - 1]; let e0 = d0_val * rhd; dsft1d = -dbdtm * dt * t23 - e0 * rad.dabt1[id_idx - 1]; dsfn1d = -e0 * (rad.dabn1[id_idx - 1] + rad.abso1[id_idx - 1] * model.densim[id_idx - 1]); for ii in 0..nlvexp { dsfp1d[ii] = -e0 * rad.dabp1[ii][id_idx - 1]; } } // 更新 DSFDT, DSFDN if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_new * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_new[ii] * fixalp.ali1[id_idx]; } } } else { // IBC == 1 的情况 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = (dsft1_curr + dbdt) * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } } else { // 标准边界条件 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_curr * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_curr; model.hein[id_idx] += d0_new * dsfn1_curr; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_curr[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } if params.ibc >= 3 { model.heitm[id_idx] -= d0_new * dsft1d; model.heinm[id_idx] -= d0_new * dsfn1d; for ii in 0..nlvexp { model.heipm[ii][id_idx] -= d0_new * dsfp1d[ii]; } } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; if model.redif[id_idx] > 0.0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_curr - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_curr - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_curr[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } if params.ibc >= 3 { model.redtm[id_idx] += d0_new * dsft1d; model.rednm[id_idx] += d0_new * dsfn1d; for ii in 0..nlvexp { model.redpm[ii][id_idx] += d0_new * dsfp1d[ii]; } } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; let _wwk = ww * abst_true; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); let d0 = ww * (fixalp.ali1[id_idx] - UN) * abst_true; let e0 = ww * (model.rad1[id_idx] - s0_curr); model.rein[id_idx] += d0 * dsfn1_curr + e0 * (rad.dabn1[id_idx] - model.sigec[ij - 1]); if params.ibc == 0 { model.reit[id_idx] += d0 * dsft1_curr + e0 * rad.dabt1[id_idx]; } else { // 改进的边界条件下的积分方程 model.reit[id_idx] += d0 * (dsft1_curr - dbdt) + e0 * rad.dabt1[id_idx] + fixalp.ali1[id_idx] / abst_true * dbdt; } for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1_curr[ii] + e0 * rad.dabp1[ii][id_idx]; } } } /// 处理 ILASCT != 0 的情况 /// 对应 Fortran GOTO 299 块 #[allow(clippy::too_many_arguments)] fn process_ilasct_nonzero( params: &Alifr1Params, fixalp: &mut FixAlp, model: &mut Alifr1ModelState, rad: &Alifr1RadState, ij: usize, nd: usize, nlvexp: usize, ww: f64, ) { // 常量 let t23 = TWO / 3.0; let t43 = 4.0 / 3.0; let t23_inv = 2.0 / 3.0; // T23 in Fortran // 初始化中间变量 let mut dsft1m: f64 = 0.0; let mut dsfn1m: f64 = 0.0; let mut dsfp1m = vec![0.0; nlvexp]; // 1. 第一个深度点 (ID=1) let id = 1; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 基本辅助量 - 源函数的导数 // 注意:这里 ABST = UN/ABSO1(ID),不同于 ILASCT == 0 的情况 let emisiv = UN / rad.emis1[id_idx]; let abst = UN / rad.abso1[id_idx]; let s0 = rad.emis1[id_idx] * abst; let dsfn1 = s0 * (rad.demn1[id_idx] * emisiv - rad.dabn1[id_idx] * abst); let dsft1 = s0 * (rad.demt1[id_idx] * emisiv - rad.dabt1[id_idx] * abst); let mut dsfp1 = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1[ii] = s0 * (rad.demp1[ii][id_idx] * emisiv - rad.dabp1[ii][id_idx] * abst); } // ID+1 的值 let idp_idx = id; let emisip = UN / rad.emis1[idp_idx]; let abstp = UN / rad.abso1[idp_idx]; let s0p = rad.emis1[idp_idx] * abstp; let mut dsfn1p = s0p * (rad.demn1[idp_idx] * emisip - rad.dabn1[idp_idx] * abstp); let mut dsft1p = s0p * (rad.demt1[idp_idx] * emisip - rad.dabt1[idp_idx] * abstp); let mut dsfp1p = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p[ii] = s0p * (rad.demp1[ii][idp_idx] * emisip - rad.dabp1[ii][idp_idx] * abstp); } // 更新 DSFDT, DSFDN 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1 * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1 * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡量 let wf = ww * model.fh[ij - 1]; if lnskip { model.fprd[id_idx] += wf * rad.abso1[id_idx] * model.rad1[id_idx] - ww * model.hextrd[ij - 1] * rad.abso1[id_idx]; let e0 = wf * model.rad1[id_idx]; let d0 = wf * rad.abso1[id_idx] * fixalp.ali1[id_idx]; model.heit[id_idx] += d0 * dsft1 + e0 * rad.dabt1[id_idx]; model.hein[id_idx] += d0 * dsfn1 + e0 * rad.dabn1[id_idx]; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0 * dsfp1[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 辐射平衡微分方程部分 model.flfix[id_idx] += wf * model.rad1[id_idx] - ww * model.hextrd[ij - 1]; model.flrd[id_idx] += model.w[ij - 1] * model.fh[ij - 1] * model.rad1[id_idx] - model.w[ij - 1] * HALF * model.extrad[ij - 1]; if model.redif[id_idx] > 0.0 { let wf = wf * fixalp.ali1[id_idx]; model.redt[id_idx] += wf * dsft1; model.redn[id_idx] += wf * dsfn1; for ii in 0..nlvexp { model.redp[ii][id_idx] += wf * dsfp1[ii]; } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); // 注意:D0 的计算不同于 ILASCT == 0 let d0 = ww * (abst_true * fixalp.ali1[id_idx] - rad.abso1[id_idx]); let e0 = ww * (model.rad1[id_idx] - s0); model.rein[id_idx] += d0 * dsfn1 + e0 * rad.dabn1[id_idx] - ww * model.sigec[ij - 1] * model.rad1[id_idx]; model.reit[id_idx] += d0 * dsft1 + e0 * rad.dabt1[id_idx]; for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 2. 深度循环 (ID = 2 to ND-1) for id in 2..nd { let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前一个点的值 dsft1m = dsft1; dsfn1m = dsfn1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } // 更新当前点为上一个点的 ID+1 值 let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfp1_curr = dsfp1p.clone(); // 更新 DSFT1, DSFN1 等 let dsft1_new = dsft1_curr; let dsfn1_new = dsfn1_curr; let dsfp1_new = dsfp1_curr.clone(); // 计算 ID+1 的值 let idp_idx = id; let emisip_new = UN / rad.emis1[idp_idx]; let abstp_new = UN / rad.abso1[idp_idx]; let s0p_new = rad.emis1[idp_idx] * abstp_new; let dsfn1p_new = s0p_new * (rad.demn1[idp_idx] * emisip_new - rad.dabn1[idp_idx] * abstp_new); let dsft1p_new = s0p_new * (rad.demt1[idp_idx] * emisip_new - rad.dabt1[idp_idx] * abstp_new); let mut dsfp1p_new = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfp1p_new[ii] = s0p_new * (rad.demp1[ii][idp_idx] * emisip_new - rad.dabp1[ii][idp_idx] * abstp_new); } dsft1p = dsft1p_new; dsfn1p = dsfn1p_new; dsfp1p = dsfp1p_new; // 更新 DSFDT, DSFDN 等 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_new * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_new[ii] * fixalp.ali1[id_idx]; } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_new; model.hein[id_idx] += d0_new * dsfn1_new; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_new[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; if model.redif[id_idx] > 0.0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_new - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_new - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_new[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); let d0 = ww * (abst_true * fixalp.ali1[id_idx] - rad.abso1[id_idx]); let e0 = ww * (model.rad1[id_idx] - s0); model.rein[id_idx] += d0 * dsfn1_new + e0 * rad.dabn1[id_idx] - ww * model.sigec[ij - 1] * model.rad1[id_idx]; model.reit[id_idx] += d0 * dsft1_new + e0 * rad.dabt1[id_idx]; for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1_new[ii] + e0 * rad.dabp1[ii][id_idx]; } } } // 3. 最深点 ID=ND let id = nd; let id_idx = id - 1; let lnskip = model.lskip[id_idx][ij - 1] == 0; // 保存前两个点的值 let dsftmm = dsft1m; let dsfnmm = dsfn1m; let mut dsfpmm = vec![0.0; nlvexp]; for ii in 0..nlvexp { dsfpmm[ii] = dsfp1m[ii]; } // 更新前一个点的值 dsft1m = dsft1; dsfn1m = dsfn1; for ii in 0..nlvexp { dsfp1m[ii] = dsfp1[ii]; } // 更新当前点为上一个点的 ID+1 值 let s0_curr = s0p; let dsft1_curr = dsft1p; let dsfn1_curr = dsfn1p; let dsfp1_curr = dsfp1p.clone(); // 初始化 ID-1 的导数(用于边界条件) let mut dsft1d: f64 = 0.0; let mut dsfn1d: f64 = 0.0; let mut dsfp1d = vec![0.0; nlvexp]; // 改进的下边界条件 let mut dbdt: f64 = 0.0; if params.ibc > 0 && params.idisk == 0 { let dt = UN / (model.deldmz[id_idx - 1] * (model.absot[id_idx] + model.absot[id_idx - 1])); let plad = model.xkfb[id_idx] / model.xkf1[id_idx]; dbdt = plad / model.xkf1[id_idx] * model.hkt21[id_idx] * model.freq[ij - 1] * dt; if params.ibc == 1 { // 简单边界条件 let dsft1_new = dsft1_curr + dbdt; if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } else if params.ibc >= 2 { // 改进的边界条件 let plam = model.xkfb[id_idx - 1] / model.xkf1[id_idx - 1]; let tau23 = t23 * dt; let tau43 = t43 * dt; let d0 = (plad * (UN + tau43) - t43 * plam * dt) * dt * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx]; let e0 = d0 * rhd; let dsft1_new = dsft1_curr + dbdt * (UN + tau23) - e0 * rad.dabt1[id_idx]; let dsfn1_new = dsfn1_curr - e0 * (rad.dabn1[id_idx] + rad.abso1[id_idx] * model.densim[id_idx]); let mut dsfp1_new = dsfp1_curr.clone(); for ii in 0..nlvexp { dsfp1_new[ii] = dsfp1_curr[ii] - e0 * rad.dabp1[ii][id_idx]; } if params.ibc >= 3 { let dbdtm = plam / model.xkf1[id_idx - 1] * model.hkt21[id_idx - 1] * model.freq[ij - 1] * dt; let rhd = model.deldmz[id_idx - 1] * model.densi[id_idx - 1]; let e0 = d0 * rhd; dsft1d = -dbdtm * dt * t23_inv - e0 * rad.dabt1[id_idx - 1]; dsfn1d = -e0 * (rad.dabn1[id_idx - 1] + rad.abso1[id_idx - 1] * model.densim[id_idx - 1]); for ii in 0..nlvexp { dsfp1d[ii] = -e0 * rad.dabp1[ii][id_idx - 1]; } } // 更新 DSFDT, DSFDN if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_new * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_new * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_new[ii] * fixalp.ali1[id_idx]; } } } } else { // 标准边界条件 if params.irder == 1 || params.irder == 3 { fixalp.dsfdt[id_idx] = dsft1_curr * fixalp.ali1[id_idx]; fixalp.dsfdn[id_idx] = dsfn1_curr * fixalp.ali1[id_idx]; } if params.irder > 1 { for ii in 0..nlvexp { fixalp.dsfdp[ii][id_idx] = dsfp1_curr[ii] * fixalp.ali1[id_idx]; } } } // 流体静力学平衡方程 if lnskip { let d0 = ww * model.fak1[id_idx]; let a0 = ww * model.fak1[id_idx - 1]; model.fprd[id_idx] += d0 * model.rad1[id_idx] - a0 * model.rad1[id_idx - 1]; let e0 = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; model.heit[id_idx] += d0_new * dsft1_curr; model.hein[id_idx] += d0_new * dsfn1_curr; model.heitm[id_idx] += e0 * dsft1m; model.heinm[id_idx] += e0 * dsfn1m; for ii in 0..nlvexp { model.heip[ii][id_idx] += d0_new * dsfp1_curr[ii]; model.heipm[ii][id_idx] += e0 * dsfp1m[ii]; } if params.ibc >= 3 { model.heitm[id_idx] -= d0_new * dsft1d; model.heinm[id_idx] -= d0_new * dsfn1d; for ii in 0..nlvexp { model.heipm[ii][id_idx] -= d0_new * dsfp1d[ii]; } } } // 辐射平衡微分方程部分 let ddt = UN / (model.absot[id_idx] + model.absot[id_idx - 1]); let dt = ddt / model.deldmz[id_idx - 1]; let fl = (model.rad1[id_idx] * model.fak1[id_idx] - model.rad1[id_idx - 1] * model.fak1[id_idx - 1]) * dt; model.flfix[id_idx] += ww * fl; if model.redif[id_idx] > 0.0 { let d0 = ww * model.fak1[id_idx] * dt; let a0 = ww * model.fak1[id_idx - 1] * dt; let d0m = d0 * fixalp.alim1[id_idx] - a0 * fixalp.ali1[id_idx - 1]; let d0_new = d0 * fixalp.ali1[id_idx] - a0 * fixalp.alip1[id_idx - 1]; let e0 = ww * fl * ddt; model.redx[id_idx] += e0 * rad.abso1[id_idx]; model.redxm[id_idx] += e0 * rad.abso1[id_idx - 1]; let e0m = e0 * model.densi[id_idx - 1]; let e0_new = e0 * model.densi[id_idx]; model.redt[id_idx] += d0_new * dsft1_curr - e0_new * rad.dabt1[id_idx]; model.redtm[id_idx] += d0m * dsft1m - e0m * rad.dabt1[id_idx - 1]; model.redn[id_idx] += d0_new * dsfn1_curr - e0_new * rad.dabn1[id_idx]; model.rednm[id_idx] += d0m * dsfn1m - e0m * rad.dabn1[id_idx - 1]; for ii in 0..nlvexp { model.redp[ii][id_idx] += d0_new * dsfp1_curr[ii] - e0_new * rad.dabp1[ii][id_idx]; model.redpm[ii][id_idx] += d0m * dsfp1m[ii] - e0m * rad.dabp1[ii][id_idx - 1]; } if params.ibc >= 3 { model.redtm[id_idx] += d0_new * dsft1d; model.rednm[id_idx] += d0_new * dsfn1d; for ii in 0..nlvexp { model.redpm[ii][id_idx] += d0_new * dsfp1d[ii]; } } } // 辐射平衡积分方程部分 if model.reint[id_idx] > 0.0 { let abst_true = rad.abso1[id_idx] - model.elscat[id_idx]; model.fcooli[id_idx] += ww * (rad.emis1[id_idx] - abst_true * model.rad1[id_idx]); let d0 = ww * (abst_true * fixalp.ali1[id_idx] - rad.abso1[id_idx]); let e0 = ww * (model.rad1[id_idx] - s0_curr); model.rein[id_idx] += d0 * dsfn1_curr + e0 * rad.dabn1[id_idx] - ww * model.sigec[ij - 1] * model.rad1[id_idx]; if params.ibc == 0 { model.reit[id_idx] += d0 * dsft1_curr + e0 * rad.dabt1[id_idx]; } else { // 改进的边界条件下的积分方程 model.reit[id_idx] += d0 * (dsft1_curr - dbdt) + e0 * rad.dabt1[id_idx] + fixalp.ali1[id_idx] / rad.abso1[id_idx] * dbdt; } for ii in 0..nlvexp { model.reip[ii][id_idx] += d0 * dsfp1_curr[ii] + e0 * rad.dabp1[ii][id_idx]; } } // 避免未使用变量警告 let _ = (dsftmm, dsfnmm, dsfpmm); } #[cfg(test)] mod tests { use super::*; #[test] fn test_alifr1_ifali_le_1() { // 测试 IFALI <= 1 时直接返回 let params = Alifr1Params { ij: 1, nd: 10, nlvexp: 5, ifali: 1, irder: 1, ilmcor: 3, ilasct: 0, ibc: 0, idisk: 0, ifalih: 0, }; // 创建空的 FixAlp(实际使用需要完整初始化) let mut fixalp = FixAlp::default(); // 简单测试:确保函数不会 panic // 实际测试需要完整的模型状态 let _ = (¶ms, &mut fixalp); } }