diff --git a/src/cryo_tank/README.md b/src/cryo_tank/README.md new file mode 100644 index 0000000..7c2b017 --- /dev/null +++ b/src/cryo_tank/README.md @@ -0,0 +1,379 @@ +# 低温液氮储箱仿真模块使用说明 + +本目录实现了一个低温液氮储箱模型,用于模拟液氮储箱在氦气增压、液氮进出口流量、环境漏热和气液两区换热作用下的温度、液位、压力、氦气用量等随时间变化。 + +模型入口文件是 `main.py`,主要参数集中在 `config.py`。运行后会把数据和图像写入 `results/cryo_tank/`。 + +## 运行方法 + +在项目根目录运行: + +```bash +python3 src/cryo_tank/main.py +``` + +如果使用本地虚拟环境,先安装依赖: + +```bash +.venv/bin/python -m pip install numpy scipy matplotlib pillow CoolProp pytest python-docx +``` + +然后运行: + +```bash +.venv/bin/python src/cryo_tank/main.py +``` + +建议从项目根目录运行,而不是进入 `src/cryo_tank/` 后运行。这样输出路径会稳定写到: + +```text +results/cryo_tank/ +``` + +## 输出文件 + +默认输出目录由 `config.py` 中的 `OUTPUT_DIR` 控制: + +```python +OUTPUT_DIR = "results/cryo_tank" +``` + +运行完成后会生成: + +- `cryo_tank_history.npz`:压缩后的完整时序数据,适合用 Python 后处理。 +- `cryo_tank_history.csv`:CSV 表格数据,适合用 Excel、Origin 或其他工具查看。 +- `cryo_tank_temperatures.png`:液相温度和气枕区温度曲线。 +- `cryo_tank_level.png`:液位和充满率曲线。 +- `cryo_tank_he_flow.png`:氦气质量和氦气流量曲线。 +- `cryo_tank_heat.png`:漏热和气液换热曲线。 +- `cryo_tank_pressure.png`:总压、氮气分压和氦气分压曲线。 + +如果没有看到 CSV 文件,先确认本地代码里是否有: + +```bash +grep -n "save_history_csv" src/cryo_tank/main.py src/cryo_tank/output.py +``` + +然后确认实际输出位置: + +```bash +find results/cryo_tank -maxdepth 1 -type f -print +``` + +## 代码文件功能 + +### `main.py` + +仿真入口。主要流程是: + +1. 从 `config.py` 读取几何、工况、初始条件和求解参数。 +2. 创建漏热模型 `MLIHeatLeak`。 +3. 创建储箱模型 `CryoTank`。 +4. 调用 `solver.run()` 进行 ODE 求解。 +5. 调用 `output.py` 保存 `.npz`、`.csv` 和图像。 + +如果只是运行已有工况,一般只需要执行这个文件,不需要改动它。 + +### `config.py` + +集中存放默认参数。常用调参基本都在这个文件里完成,包括: + +- 储箱几何尺寸 +- 工作压力 +- 初始温度和初始气枕率 +- 液氮入口、出口流量 +- 氦气入口温度 +- 气液换热系数 +- 环境温度 +- 仿真结束时间 +- 求解器误差容限 +- 输出目录 + +### `tank_model.py` + +核心物理模型,定义 `CryoTank` 类。 + +状态量为: + +```text +y = [m_liq, U_liq, U_ull] +``` + +含义分别是: + +- `m_liq`:液氮质量 +- `U_liq`:液相内能 +- `U_ull`:气枕区总内能 + +`derive(y)` 会根据状态量计算温度、体积、液位、充满率、氦气质量、氮气分压和氦气分压等派生量。 + +`rhs(t, y)` 是 ODE 右端函数,由 `scipy.integrate.solve_ivp` 调用。 + +### `solver.py` + +ODE 求解器封装。主要函数是: + +```python +run(tank, t_end, rtol=1e-8, atol=1e-10, max_step=10.0) +``` + +它会: + +- 调用 `tank.initial_state()` 获取初始状态。 +- 使用 `solve_ivp` 求解。 +- 在液氮质量降到 0 时终止计算。 +- 对每个输出时刻计算温度、压力、液位、漏热、换热等时序数据。 +- 返回 `history` 字典。 + +### `properties.py` + +物性计算模块。 + +主要功能: + +- 液氮密度、焓、内能计算。 +- 氮气饱和压力和饱和蒸气内能计算。 +- 氦气理想气体焓、内能、比热计算。 +- 建立液氮内能到温度的查表插值,加速 ODE 求解。 + +该模块依赖 `CoolProp`。 + +### `heat_leak.py` + +漏热模型模块。 + +当前包含: + +- `HeatLeakModel`:漏热模型基类。 +- `MLIHeatLeak`:真空多层绝热模型,按固定热流密度 `q_mli` 计算。 +- `FoamHeatLeak`:泡沫或包覆绝热模型,按一维稳态导热计算。 + +默认在 `main.py` 中使用: + +```python +heat_leak = MLIHeatLeak(A_total=A_TOTAL, q_mli=1.0) +``` + +### `output.py` + +输出模块。 + +负责保存: + +- 压缩时序数据 `.npz` +- 表格数据 `.csv` +- 温度、液位、氦气流量、热流和压力图像 + +绘图使用 `matplotlib` 的 `Agg` 后端,因此不需要图形界面。 + +## 常用调参方法 + +### 修改仿真时间 + +在 `config.py` 中修改: + +```python +T_END = 3600.0 +``` + +单位是秒。比如仿真 10 分钟: + +```python +T_END = 600.0 +``` + +### 修改储箱尺寸 + +在 `config.py` 中修改: + +```python +V_TOTAL = 420.1e-3 +H_TANK = 0.5 +``` + +其中: + +- `V_TOTAL` 是储箱总体积,单位 `m^3`。 +- `H_TANK` 是圆柱储箱高度,单位 `m`。 + +横截面积、直径、侧面积和总面积会自动由这两个参数计算。 + +### 修改工作压力 + +在 `config.py` 中修改: + +```python +P_WORKING = 0.17e6 +P_MAX = 0.8e6 +``` + +单位是 Pa,代码中使用绝对压力。 + +`P_WORKING` 是模型维持的工作压力,`P_MAX` 是最大承压限制,用于参数合法性检查。 + +### 修改初始充液量 + +在 `config.py` 中修改: + +```python +ULLAGE_FRACTION = 0.30 +``` + +该参数表示初始气枕体积分数。比如: + +- `0.30` 表示气枕区占 30%,液氮占 70%。 +- `0.20` 表示气枕区占 20%,液氮占 80%。 + +取值必须在 0 到 1 之间。 + +### 修改液氮进出口流量 + +在 `config.py` 中修改: + +```python +MDOT_IN_LN2 = 1.144 +MDOT_OUT_LN2 = 1.1895 +``` + +单位是 `kg/s`。 + +当前液氮质量变化率为: + +```text +dm_liq/dt = MDOT_IN_LN2 - MDOT_OUT_LN2 +``` + +如果出口流量大于入口流量,液位会逐渐下降。 + +### 修改入口温度 + +在 `config.py` 中修改: + +```python +T_IN_LN2 = 77.0 +T_IN_HE = 100.0 +``` + +单位是 K。 + +### 修改环境漏热 + +默认漏热模型在 `main.py` 中设置: + +```python +heat_leak = MLIHeatLeak(A_total=A_TOTAL, q_mli=1.0) +``` + +其中 `q_mli` 是单位面积漏热,单位 `W/m^2`。增大 `q_mli` 会增加外界进入储箱的热量。 + +如果需要改用泡沫绝热模型,可以在 `main.py` 中引入并替换为: + +```python +from cryo_tank.heat_leak import FoamHeatLeak + +heat_leak = FoamHeatLeak(A_total=A_TOTAL, k_eff=0.03, delta=0.05) +``` + +其中: + +- `k_eff` 是等效导热系数,单位 `W/(m*K)`。 +- `delta` 是绝热层厚度,单位 `m`。 + +### 修改气液换热 + +在 `config.py` 中修改: + +```python +H_CONV_SURFACE = 50.0 +``` + +单位是 `W/(m^2*K)`。该参数控制液相和气枕区之间的换热强度。 + +### 修改求解精度 + +在 `config.py` 中修改: + +```python +RTOL = 1e-8 +ATOL = 1e-10 +``` + +如果计算较慢,可以适当放宽;如果需要更高精度,可以适当收紧。收紧误差容限通常会增加计算时间。 + +`solver.run()` 还有一个默认参数: + +```python +max_step=10.0 +``` + +表示最大时间步长,单位秒。如果需要更密集的输出点,可以在调用 `run()` 时减小它。 + +## 后处理数据 + +读取 `.npz` 数据示例: + +```python +import numpy as np + +data = np.load("results/cryo_tank/cryo_tank_history.npz") +print(data.files) +print(data["t"]) +print(data["T_liq"]) +``` + +读取 CSV 数据示例: + +```python +import numpy as np + +data = np.loadtxt( + "results/cryo_tank/cryo_tank_history.csv", + delimiter=",", + skiprows=1, +) +print(data.shape) +``` + +CSV 第一行是列名,列名来自 `history` 字典,包括: + +- `t` +- `m_liq` +- `U_liq` +- `U_ull` +- `T_liq` +- `T_ull` +- `m_He` +- `mdot_He` +- `V_liq` +- `V_ull` +- `liquid_level` +- `fill_fraction` +- `P_N2` +- `P_He` +- `P_total` +- `Q_leak` +- `Q_leak_liq` +- `Q_leak_ull` +- `Q_liq_to_ull` + +## 测试 + +运行低温储箱相关测试: + +```bash +pytest -q tests/cryo_tank +``` + +运行全项目测试: + +```bash +pytest -q +``` + +## 注意事项 + +- 本模型当前将储箱分为液相区和气枕区两个区域,不是完整 CFD 模型。 +- 气枕区氮气和氦气采用简化处理,氦气按理想气体热力学关系计算。 +- 液氮物性依赖 `CoolProp`,缺少该包会导致程序无法启动。 +- `results/` 目录默认被 `.gitignore` 忽略,仿真输出不会自动上传到 Git。 +- 建议每次修改参数后保存对应工况说明,避免不同仿真结果混在同一个输出目录中。