原生结果series通过字节索引直传,C端使用Ryu精确回读编码和64 KiB批量写出;网页采用Float64缓存和CSV工作线程,减少结果处理与保存等待。 补充八路AME曲线核查、全流程分阶段计时、独立编码基准和复现工具,固定后续优化采用修正八路及rtol=1e-8。C写出1.1808→0.1638 s,点击到可查看8.0100→6.9756 s。 验证:最终10项编码专项、29项相关后端回归通过;8份原生结果逐位一致,16次网页结果/CSV/刷新恢复通过。前端构建及缓存/CSV专项在本轮结果处理工作中通过。环境、原始大结果与临时构建不纳入Git。
22 KiB
八路模型计算效率与网页阶段计时(2026-09-11)
本轮以 808c484 的正式代码和 test-mql-8-corrected.json 为主案例。八路在当前默认精度下完整运行,未退回四路。本轮增加独立诊断脚本和运行记录,没有修改生产算法、工程参数或输出采样。后续遵循 八路优先的优化验证约定。
运行范围与可复现条件
- 工程 SHA256:
670977bef67e62d9c66e8af497bada208bd72a7301be45128d185d47282cf288;CLI XML SHA256:2804b33f04cabb3c10fcc3cc0843c35de17efbe1b6ee5e5e821edd9a5515a23d。对应 AME 为tests/data/test_mql.ame,SHA2561ff0ea4284b9248260eeceb8b27cd0bc14dbccb43554ab8c0b49900d0b944c3d。 - 157 元件、178 条连接、132 连续状态;返回 1784 个变量、1002 个原始采样点(含事件点),仿真 0~10 s,输出间隔 0.01 s。
- CVODE BDF / SUNDIALS 7.4.0,
rtol=1e-8,max_step=1e30;自动首步。实际绝对误差限按状态生成:质量1e-14 kg、内能1e-8 J、速度1e-12 m/s、位移1e-12 m,并非对所有状态统一使用配置对象中的atol=1e-8。数值雅可比、稠密线性求解和事件处理策略保持生产设置。 - Linux x86_64 虚拟机,Intel Xeon Silver 4210R @ 2.40 GHz,16 逻辑 CPU、约 30 GiB 内存;GCC 13.3.0、Python 3.12、Node 24.18.0、Chromium 151.0.7922.34。原生进程主要为单核计算,环境与构建哈希保存在原始记录。
- 各组预热一次、正式运行三次;中位数与范围单列。三算法组交错执行;网页对照组与分阶段插桩组串行执行,不同时运行诊断求解、绘图或大编译。样本数较少,组间百分之几的差异不作为显著优化结论。
管流算法效率与触顶情况
三算法使用同一 corrected 八路、物性复用实现和全系统积分精度。固定点版本仅在明确的 5d5a2e1 基线上恢复原半步松弛管流循环,其余生产数值逻辑保持一致;不是运行旧版整个应用。前次牛顿取自该提交,当前保护牛顿取自本轮正式内核。此组没有逐次调用计数插桩。
| 算法 | 纯求解中位数(范围)/ s | 进程全程中位数 / s | RHS 次数 | 接受 / 拒绝步 |
|---|---|---|---|---|
| 旧固定点,16 / 64 轮上限 | 12.0976(11.9926~12.1511) | 14.2514 | 119058 | 9647 / 679 |
| 前次牛顿 | 5.8183(5.7829~5.8944) | 7.9144 | 74265 | 6974 / 454 |
| 当前保护牛顿+二分回退 | 5.9138(5.9115~5.9323) | 7.9698 | 74265 | 6974 / 454 |
相对旧固定点,当前纯求解时间减少 51.12%、速度约 2.05 倍,进程全程减少 44.08%,RHS 次数减少 37.62%。相对前次牛顿,本组耗时增加约 1.64%,不能宣称保护机制带来额外提速;两版牛顿的完整采样、最终输出和状态逐值相同。
另用未经本轮插桩的正式构建独立运行一次预热、三次正式检查:纯求解中位数 5.7972 s(5.7897~5.8214),进程全程 7.8504 s(7.8437~7.8685),均完成 10 s;每次 RHS 74265、接受 6974、拒绝 454、雅可比 475、线性分解 1656、状态转换 1、求解器启动 4。该组构建缓存命中,输入准备 0.1493 s、构建/缓存核验 0.03294 s;这些准备时间在三个进程运行前发生一次,不包含在纯求解时间内。单独组的 5.80 s 不与上一组旧算法拼接计算加速比。
为区分算法本身和积分轨迹变化,另对三版内核进行独立计数诊断:先各自跑完整八路,再将当前轨迹的 3,081,320 组实际管阻方程输入全部原样重放给三个版本,不抽样、不去重。诊断耗时不用于上述性能比较。
| 同一组管阻输入的计数 | 旧固定点 | 前次牛顿 | 当前保护牛顿 |
|---|---|---|---|
| 解析返回 / 迭代求解 | 0 / 3081320 | 2370685 / 710635 | 相同 |
| 累计循环轮数 | 49431317 | 3081555 | 相同 |
| 单次最多轮数 | 64 | 6 | 6 |
| 进入最后允许轮次 | 3037792(98.587%) | 0 | 0 |
| 耗尽额度且未满足各自停止条件 | 3010570(97.704%) | 0 | 0 |
| 实际返回值的统一相对残差 > 1e-9 | 3072455 | 0 | 0 |
| 二分回退 / 非有限返回 | 0 / 0 | 0 / 0 | 0 / 0 |
牛顿累计轮数减少 93.766%。710635 次迭代调用分别用 3 轮 74290 次、4 轮 361601 次、5 轮 236183 次、6 轮 38561 次。当前案例没有触发二分或失败路径,所以它验证了正常输入的效率和一致性,不能代替极端状态下的保护测试,也不能证明任意系统必然收敛。
“进入最后一轮”与“耗尽仍未满足条件”分开统计:固定点 PNL00R 的 64 轮分支有 1638 次进入最后一轮、但没有耗尽失败;真正耗尽的都来自其他管路的 16 轮分支。旧循环满足自身停止条件的 70750 次中,61885 次仍不满足当前统一方程残差门槛;相对残差超标不直接代表同等数量的大绝对流量误差。
各自完整积分轨迹上,旧固定点实际管阻调用 5041645 次、耗尽 4937544 次;两版牛顿均为 3081320 次、耗尽 0 次。零压差 247634 次和 PNL00R 直接层流 235766 次另计,未混入混合摩擦方程残差。当前插桩结果与独立正式构建的 series/final/finalState 逐值相同。
该八路在积分 RHS 中请求管流缓存 2970600 次,命中 0;另有 594120 次直接调用。物性复用与这项管流缓存不同;此结果只说明本例可进一步评估缓存查找的成本,不能直接推广到其他拓扑或据此删除缓存。
真实网页主流程与额外操作成本
使用正式 Vite 静态构建,经 Playwright 驱动 Chromium;无模拟 API、预制结果注入或重复读取响应体。独立对照服务 127.0.0.1:8013 不加载诊断插桩;分阶段服务 127.0.0.1:8012 仅在隔离 C 主程序中增加稀疏时钟,并包装实际后台函数。两个服务的求解器和元件文件逐字节相同,前端构建集合 SHA256 同为 2faa6ce32ee9997187870d64af2bc235a830eb7b8def7749ddcb0eaeeed4831e;计时脚本 SHA 也相同。
每组预热一次、正式三次。每轮从公开 JSON 导入入口加载同一 corrected 文件,公开导出工程后逐项验证全部参数、端点和仿真设置,然后点击运行;导入与核查不包含在点击运行计时中。每轮继续打开结果页、选择指定管路温度、下载 CSV 与结果文件,再刷新并核对恢复结果。结果页和温度曲线立即打开,允许浏览器 IndexedDB 异步保存与查看过程自然重叠。
下表单位为秒,格式为 中位数(最小~最大)。对照组是常规网页成本的主记录;“首次绘制机会”指可见 DOM 后经过两次 requestAnimationFrame,未测量 GPU 完成时间。
| 阶段 | 对照组 / s | 分阶段组 / s |
|---|---|---|
| 工程导入 change → 画布首次绘制机会 | 0.2527(0.2273~0.2862) | 0.2312(0.2251~0.2411) |
| 点击运行 → 完成状态 DOM | 9.8716(9.7697~9.8826) | 9.7777(9.7358~9.8408) |
| 点击运行 → 完成状态首次绘制机会 | 9.8989(9.7840~9.9104) | 9.8005(9.7596~9.8660) |
| 点击运行 → 结果页首次绘制机会(自动切页) | 10.1516(10.0600~10.1834) | 10.0589(10.0305~10.1056) |
| 点击运行 → 温度曲线首次绘制机会(自动选曲线) | 10.6899(10.5762~10.7431) | 10.6160(10.5916~10.6433) |
| 点击运行 → 观察到 IndexedDB 保存完成指针 | 12.2922(11.8303~12.4076) | 12.4344(11.5322~12.4967) |
| 进入结果页 → 首次绘制机会 | 0.1910(0.1893~0.1980) | 0.1927(0.1832~0.1946) |
| 选择温度 → 曲线首次绘制机会 | 0.0269(0.0262~0.0297) | 0.0276(0.0233~0.0293) |
| CSV 点击 → 下载并保存 | 5.6198(5.5717~5.6381) | 5.5732(5.4253~5.6625) |
| 结果文件点击 → 下载并保存 | 1.2308(1.2265~1.3213) | 1.2921(1.1552~1.5145) |
| 刷新导航 → 已恢复结果首次绘制机会 | 0.5885(0.5406~0.6592) | 0.5487(0.5074~0.5630) |
无插桩对照组的 C 纯求解中位数为 6.0653 s、进程全程 7.9499 s;独立 CLI 的 5.7972 s 属另一运行环境下的分组结果,不把差值直接归因于网页某项 CPU 工作。分阶段组点击到完成绘制为 9.8005 s,对照为 9.8989 s,相差约 -0.99%;本组三次样本未见明显端到端插桩增量,也不能把该负差当作加速。持久化和导出波动更大,逐次原始值均保留。
初次导航只记录每组一次:HTML loadEventEnd 对照 0.0971 s、分阶段 0.1086 s;Playwright 观察到工程导入控件时分别为 0.5628 / 0.6064 s,包含自动化观察与调度延迟,不是严格的首次可交互时间。首次工程导入到两帧观察点,对照预热为 0.3716 s;三次重复导入中位为 0.2527 s。页面加载、导入、仿真、查看与导出分别记录,未用自动化操作间隙拼成一个“纯网页耗时”。
“DOM 稳定”另取 120 ms 无变动再等两帧:结果页中位 0.3710 s、温度曲线 0.1736 s、刷新恢复 0.7575 s(对照)。这包含人为安静窗口,不能把它全称为渲染工作。下载完成包含 Playwright 通知、saveAs 与文件系统开销,不等于浏览器内序列化 CPU 时间。
后台内部各阶段
用每个请求的 X-Simulation-Id 将网页与后台记录一一关联。下表为分阶段组正式三次的秒数;所列主要阶段在单个请求内依次发生。各阶段分别取中位数,故其相加不保证等于总耗时中位数。
| 阶段 | 中位数(最小~最大)/ s |
|---|---|
| XML 校验 | 0.0231(0.0222~0.0246) |
| 网络编译 | 0.0364(0.0361~0.0465) |
| 系统 C 代码生成 | 0.0542(0.0528~0.0548) |
| 构建缓存核验(3 次均命中) | 0.0321(0.0308~0.0331) |
| C 参数准备 | 0.0000503 |
| C 初始化与初始采样 | 0.0001(0.0001~0.0001) |
| C 纯积分 | 6.0855(6.0414~6.0994) |
| C 最终采样/状态处理 | 0.0000029 |
| C 最终及全采样输出投影 | 0.0855(0.0837~0.0861) |
| C 结果 JSON 格式化并写文件 | 1.1707(1.1656~1.1945) |
| Python 读文件并 UTF-8 解码 | 0.0360(0.0321~0.0429) |
| Python 解析原生 JSON | 0.5513(0.5429~0.5588) |
| 进程启动/等待/退出等未细分余量 | 0.0029(0.0025~0.0029) |
| 结果接口元数据组装 | 0.0330(0.0245~0.1175) |
| 最终 NDJSON 结果事件序列化 | 1.1928(1.1862~1.2106) |
| 序列化结束 → ASGI 最后响应体发送完成 | 0.1715(0.1489~0.1808) |
| HTTP 其余编排/调度余量 | 0.0124(0.0114~0.0155) |
后台 HTTP 全程中位 9.5123 s(9.4458~9.5845)。内部 C main 全程 7.3380 s,Python 原生执行与结果读取包装 7.9194 s,仿真 worker 全程 8.1380 s;这些是包含上表子阶段的父区间,不能再次相加。ASGI send 的累计 await 为 0.0701 s,可与生成结果的后台任务重叠,亦不代表客户端网络总时间。诊断产物保留另耗约 0.00066 s,已包含在原生执行包装中。
约 2.95 s 用于 C 的 JSON 写出、Python 读取解析及 HTTP 结果 JSON 序列化,约为后台总程的 31%;相比之下输出物理量投影仅约 0.086 s。这里先定位到文本结果处理成本,并未将整个差额笼统归为物性或求根。
正式网页八次运行均复用已构建的程序。唯一冷构建来自功能预检:编译/核验 3.4154 s,构建键 bcb85b5dce729fe9b7a503919b720be03950ff31839877edd344377d4ee9cfc0 与后续完整八路分阶段组相同;预检将运行终点设为 0.02 s,只改变运行时选项,未改变编译出的系统程序。这个单次冷编译时间可供首次运行成本参考,但本轮没有测得完整 0~10 s 的冷启动网页总时间,不把预检总时间冒用为正式结果。
浏览器内部、持久化和导出细分
分阶段组保留了原始 fetch、流读取、解码、JSON.parse、IndexedDB 事务和下载锚点的时间戳,没有克隆响应或重复解析。
| 观察区间 | 中位数 / s | 含义与边界 |
|---|---|---|
| 点击运行 → 调用 fetch | 0.0234 | 含前端模型检查、快照/XML 和提交准备,未单独计 XML CPU |
| fetch → 收到响应头 | 0.0298 | 收到流式响应头,不表示仿真已经算完 |
| 响应头 → 读到流 EOF | 9.6765 | 包含后台计算、传输、消费者处理与调度 |
| 累计未完成的流 read 等待 | 9.4636 | 含后台结果尚未生成的等待,不能称为纯网络时间 |
| 最终结果的原始 JSON.parse | 0.1125 | 同步解析仅执行一次 |
| 全部流消息 JSON.parse | 0.1139 | 已含上一行 |
| UTF-8 decode 累计 | 0.0280 | 原始解码调用,不包含分片扫描/拼接 |
| 最终 JSON.parse 结束 → 完成 DOM | 0.0430 | 含应用处理和 React 调度,未独立测 React CPU |
| 结果解析结束 → IndexedDB 完成指针发布 | 2.6279 | 含批处理、事务等待与调度,可与看图重叠 |
| 首次保存事务 → 完成指针发布 | 2.5952 | 仍是异步区间;不是磁盘或主线程独占时间 |
| CSV 点击 → fetch | 0.2641 | 包含将整份结果再次 JSON.stringify 的提交准备 |
| CSV fetch → 响应头 | 4.6968 | 含浏览器请求准备、后台处理及网络/调度 |
| CSV 点击 → Blob 下载锚点 | 5.0143 | 浏览器已经取得并准备好下载数据 |
| 结果文件点击 → Blob 下载锚点 | 0.6113 | 包含结果文件序列化及 Blob 准备 |
最终流式响应约 33.73 MB;原生结果 JSON 为 32,725,293 字节,CSV 为 32,346,795 字节,结果文件约 33.85 MB(十进制 MB)。本次是本机回环 HTTP,未模拟远端带宽、TLS 或网络延迟;不能把这些网络相关耗时直接推广到远端部署。
CSV 后台另有独立请求,按请求顺序和时间戳关联,正式三次分段如下:
| CSV 后台阶段 | 中位数(最小~最大)/ s |
|---|---|
| ASGI 开始 → 收完请求体 | 0.0262(0.0247~0.0285) |
| 收完请求体 → CSV 函数开始 | 0.7072(0.7010~0.7138) |
| CSV 校验、逐单元格式化与文本组装 | 2.3684(2.3616~2.3885) |
| CSV 函数结束 → HTTP 完成 | 0.1252(0.1221~0.1264) |
| CSV HTTP 全程(父区间) | 3.2264(3.2177~3.2494) |
“收完请求体→CSV 函数”约 0.707 s,涵盖路由层 JSON 解码、模型校验及调度,未再将每项 CPU 时间拆开。CSV 浏览器 fetch 到响应头比 ASGI 全程更长;跨进程请求准备、发送及调度的余量未进一步归因。CSV 的完整结果往返及文本组装成本已经实测,后续可据此单独优化。
本轮验证与下一步优先级
两组共 8 次网页运行均完成 10 s,且无 pageerror。每轮公开导出的工程参数与连接全部匹配固定输入;结果页、精确单位 K 的温度曲线、CSV、.simresult 下载和刷新恢复均通过。8 份 CSV 均为 1785 列 × 1002 数据行,合计 14,308,560 个数值单元与独立原生结果精确相等;全部 series/final 也精确相等,刷新前后完整结果一致。4 份后台稀疏插桩原生文件的 series/final/finalState 均与生产文件逐值相同。56 个唯一气体质量状态用 math.fsum 汇总,初始总质量 5.566893015 kg,最大漂移 1.15463e-14 kg;所有保存数值有限。
初次自动化预检曾误用旧控制台 CSS,另一次重复组在刷新后假定建模工程自动恢复而未提交新请求。这两类脚本失败保存在 browser-stage-smoke/ 与 browser-control-failed/,明确排除正式统计。最终脚本使用当前 DockedSimulationConsole、每轮重新导入并核对工程,两个完整正式组均通过。0.02 s 的功能预检只证明操作流程,不混入八路完整计算效率。
依据本轮数据,后续优先考虑:
- 先追踪八路早期压力/温度差和碰撞事件输出。 参数对齐与局部求根成功不能代替整条曲线正确性;保留八路主案例,继续固定当前输入与精度。
- 减少结果反复文本化。 当前 C 写 JSON、Python 再解析、HTTP 再序列化合计约 2.95 s;优化这条路径时仍需保留全部变量、采样、浮点数值与输出合同。
- 单独优化 CSV 与浏览器持久化。 CSV 全量回传后台并组装文本明显影响使用时间;持久化约 2 s 以上、且与查看曲线重叠,适合分别评估批大小、复制与调度,不能把保存等待计为绘图耗时。
- 继续剖析 RHS/雅可比等求解成本。 管流触顶已经为零,当前再削减迭代上限没有实测依据。可先评估本例零命中的管流缓存和 74265 次 RHS 的组成;更改雅可比或缓存策略后仍按同一八路、同精度和完整输出复核。
图中三算法与浏览器操作取三次中位数;后台堆叠图选 HTTP 总耗时居中的单个请求,所有片段可相加。浏览器各操作区间不能相加;完整可缩放图为 SVG。
与当前 Amesim 归档的对照
本次找到可用的八路保存曲线。独立核对当前 AME 内的图纸、参数数据、编译 C、状态与变量索引及初值,未发现此前四路归档中那种图纸/缓存错配;完整说明见 当前八路归档与曲线核查。使用的是当前 AME SHA,未套用绑定另一归档的历史八路冻结基准。
选取全部 132 个连续状态对应的压力、温度、位移与速度,另加阀流量、接触力、限位力和间隙,共 176 条曲线;明确映射表压/绝压、SI 单位与接口方向,分别在双方原始保存网格上线性插值对照,不删去原生事件点。下表为 AME 保存网格上各类最差曲线的最大差及该曲线 RMS,不是把全类所有点混算的 RMS。
| 量 | 最大绝对差 | 对应曲线 RMS |
|---|---|---|
| 压力 | 163395.189 Pa | 7170.441 Pa |
| 温度 | 105.215279 K | 5.829065 K |
| 阀质量流量 | 0.002990901 kg/s | 0.000114014 kg/s |
| 接触力(AME 保存网格) | 5131.971 N | 225.218 N |
最大压力、温度和此表接触力差在 0.01 s,不能全归因于后续碰撞采样时刻不一致。原生另有 t=0.9833956321732664 s 的原始事件点,8 个接触力约 4.035×10¹¹ N;AME 只保存相邻 0.98 / 0.99 s 点,无法据其线性插值判断 Amesim 精确事件时刻或是否也有极窄峰。当前 AME 的 UD00 输入含 1e17 初始信号,双方公共质量元件都出现极大位移/速度,也不能把“数值有限”当成物理合理性证明。本轮未修改这些 AME 参数。
因此,八路运行与计时记录完成,不等于八路曲线一致性验收通过。目前没有八路专用接受阈值,也缺少足够密的 AME 事件输出;保留差异供后续核查,不为通过而放宽门槛或换四路。
Amesim 耗时对比跳过:当前环境没有可调用的 Amesim,归档也没有可信 CPU/墙钟记录;.ameperf 中的时间是仿真事件时刻。归档名义容差为 1e-7,本轮为 1e-8,也不能冒称同精度速度比较。没有重跑 Amesim,没有从 10 s 仿真终点或文件时间戳推算耗时。
记录、脚本与复现
所有输入快照、编译程序、完整曲线、下载文件和浏览器截图都放在 Git 忽略目录 test/,环境仍在 .venv/native/,未纳入 Git。报告引用的相对路径在仓库本地可打开;这些大型运行产物不随 Git 克隆传递。
- 三算法原始基准、三算法汇总、正式构建独立基准。
- 完整管阻计数与同输入重放、插桩与生产逐值核对。
- 阶段汇总 JSON、阶段汇总 CSV、网页对照组、网页分阶段组。
- 网页与 CSV 全量相等核查、后台插桩逐值核查、质量守恒;每个后台请求在
test/mql8-efficiency-20260911/backend-profile/requests/<simulationId>/保存执行 XML、原生 JSON、日志和阶段时间。 - 后台分阶段诊断脚本、真实浏览器计时脚本、管阻计数脚本。网页结果复核脚本。这些都是手动诊断入口,生产服务无需加载。
# 八路三算法基准;目录必须为新目录
.venv/bin/python tests/manual/benchmark_native_pipe_solver.py \
tests/data/test-mql-8-corrected.json --output-dir test/new-mql8-variants --runs 3
# 正式构建独立基准
.venv/bin/python -m app.simulation.native_codegen tests/data/test-mql-8-corrected.json \
--output-dir test/new-mql8-production --runs 3 --timeout 120
# 后台阶段记录服务;需要已有 frontend/dist,选空闲端口
.venv/bin/python tests/manual/backend_stage_profile.py \
--output-dir test/new-mql8-backend --port 8012
# 另一个终端:--plain 为无诊断插桩的对照服务
.venv/bin/python tests/manual/backend_stage_profile.py --plain \
--output-dir test/new-mql8-control --port 8013 \
--frontend-dist test/new-mql8-backend/frontend
# Chromium 所需依赖仅使用仓库现有忽略环境
export LD_LIBRARY_PATH="$PWD/.venv/native/browser-libs/usr/lib/x86_64-linux-gnu${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}"
.tools/node-v24.18.0-linux-x64/bin/node tests/manual/browser_stage_profile.mjs \
--output test/new-mql8-browser-control --url http://127.0.0.1:8013 --mode control --runs 3
.tools/node-v24.18.0-linux-x64/bin/node tests/manual/browser_stage_profile.mjs \
--output test/new-mql8-browser-profiled --url http://127.0.0.1:8012 --mode profiled --runs 3
