拓冰建站拓冰建站
首页 / 资讯中心 / 正文

HTRI二次开发教程(09):结果取数——从对象模型与报表导出到 DataFrame

HTRI二次开发教程09结果取数——从对象模型与报表导出到 DataFrame版本与事实声明版本锚点当前Xchanger Suite 9.4。9.4 在 Final Results Report 中新增temperature effectiveness冷热两侧温度有效度等输出项说明报表内容随版本演进——解析脚本必须容错。官方 Outputs 含 spreadsheet-style output reports可导出 Excel、Summary reports、Detailed reports局部剖面、标准 TEMA specification sheet、2D/3D drawings、user-defined graphs。示例代码中所有标识符为占位符数值均为示例性建模不代表任何标准规定。一句话结论结果取数有两条路——对象模型逐字段读取精确、可控、依赖探测所得标识符与报表导出件解析稳、可审计、依赖 Excel 文件结构工程上的最优解是两者并用用对象模型取少量关键指标入账本用报表导出件做完整结果归档与交叉校验最后统一规范化成案例编号 × 指标 × 单位的长表。〇、本篇要解决的认知问题Q1对象模型取数与报表导出件解析各自的长处与短处是什么Q2summary 报表与 detailed 报表在结构上有什么本质差异为什么 detailed 不能简单一键转表Q3Xist 支持多单位集取数时单位不统一会带来什么后果怎么防Q4导出件解析时列契约column contract为什么比列名更重要Q5怎么把两条取数路的结果统一成一张可分析的长表一、机制解析1.1 两条取数路维度对象模型取数报表导出件解析数据来源Automation Server 对象树的输出字段导出的 spreadsheet-style reportExcel精度控制高可精确定位单字段中受导出格式/分页影响依赖探测所得真实标识符U2Excel 文件结构随版本漂移批量速度快内存直读慢需落盘再解析审计留痕弱只留你记录的值强导出件即原始凭证推荐组合取关键指标入账本完整归档 交叉校验为什么两条都要对象模型取数适合批量循环里取 3~5 个关键量但它不提供官方版式的原始记录。报表导出件是可交给第三方复核的凭证。生产系统里账本关键指标 报表归档是标配。1.2 summary 与 detailed 的结构差异Summary reports一两页的总览结果——整体传热系数、总压降、裕量、热负荷等标量。结构接近键-值表适合逐行解析成宽表。Detailed reports温度、压力、传热系数、热流等局部剖面——沿换热器长度/区段的一系列值。结构是多组剖面曲线每组的自变量位置与因变量多个参数不同。反直觉点detailed 报表不能简单读成一张二维表——它是一组表的集合。硬塞进一个 DataFrame 会得到一张稀疏、错位的表。正确做法是先按区段/剖面分组再各自成表long formatsection, position, parameter, value。1.3 多单位集取数的隐形地雷Xist 官方明确支持input and output can be displayed inmultiple unit sets, including user-defined sets。Dynamic display of values in all unit sets. 这带来一个陷阱同一个量在不同单位集下数值不同而导出件用哪套单位取决于案例设置。铁律级实践落盘时每个数值必须带单位或全系列统一到一套 SI 单位。禁止裸数字入库。做法在列契约里显式声明每个指标的unit取数时若发现单位与契约不符走显式换算表如 kPa↔Pa、mm↔m换算因子写死在代码里并注释来源绝不用数字看起来像来猜单位。1.4 列契约与缺失值列契约规定每列的规范名、单位、数据类型、允许缺失、来源对象模型/报表。它比列名更重要的原因是列名会变版本漂移、语言切换契约不变。解析脚本按契约校验列名只是契约到具体文件的映射。缺失值处置三态缺失真的没有、不适用该模式/该模块无此项、解析失败格式变了。三者语义不同不能一律填 0 或 NaN——否则后期无法区分设备没这项和程序没读到。1.5 取数的三条精度纪律纪律一取数必须发生在运行完成之后。第 07 篇已强调对象模型读的是当前案例的输出字段若在 run 完成前读你拿到的是上一轮或空值。取数脚本的第一行逻辑应是确认本次运行已完成而不是直接开始读。纪律二同一指标跨来源必须交叉校验。对象模型与报表导出件是两条独立的路它们的差值就是你的取数可信度。若两条路结果一致说明取数链路可靠若不一致要么单位没对齐要么其中一条路读错了字段。永远不要只走一条路就宣布取数成功——交叉校验是免费的验证。纪律三精度不四舍五入到看不清差异。报表导出件常自带位数截断对象模型读到的是完整精度。做交叉校验时用对象模型的全精度值做基准报表只作旁证若把两边都先截断到 2 位再比会掩盖真实的单位错误1000 倍偏差截断后仍是 1000 倍但小偏差会被吃掉。一条反直觉提醒“取到的数不等于可用的数”。取数是技术动作可用性是工程判断——一个传热系数取出来了但它是不是对应设计工况、是不是在清洁状态、单位是不是设计单位集都需要在取数时同步记录上下文第 12 篇的振动几何上下文就是同一思想。脱离上下文的数等于没取。二、完整代码与逐行剖析代码 9-1报表导出件解析为规范化长表# -*- coding: utf-8 -*- parse_report.py —— 把 Xist 导出的报表解析为规范化长表 用法python parse_report.py export.xlsx case_0001 输出results_long.csvcase_id, section, parameter, value, unit, source 说明导出件版式随版本漂移本脚本按内容定位 列契约的思路解析 所有数值均示例性建模不对应任何真实装置。 importsysimportreimportpandasaspd# 列契约规范名 - (单位, 类型, 允许缺失)CONTRACT{整体传热系数:(W/(m2·K),float,False),壳侧压降:(kPa,float,False),管侧压降:(kPa,float,False),热负荷:(kW,float,False),}# 显式换算表把导出件可能出现的单位统一到契约单位CONV{(壳侧压降,Pa):0.001,# Pa - kPa(壳侧压降,kPa):1.0,(管侧压降,Pa):0.001,(管侧压降,kPa):1.0,(整体传热系数,W/m2-K):1.0,# 归一化写法 - 契约写法}defnorm_unit(u):return(str(u).strip().lower().replace(·,-).replace(^,).replace( ,))deflocate_header(raw,keys,max_scan40):foriinrange(min(max_scan,len(raw))):txt | .join(str(x)forxinraw.iloc[i].tolist())ifall(kintxtforkinkeys):returnireturnNonedefparse_summary(path,case_id):rawpd.read_excel(path,headerNone,engineopenpyxl)hdrlocate_header(raw,[参数,数值])orlocate_header(raw,[Parameter,Value])rows[]ifhdrisNone:returnrows bodyraw.iloc[hdr1:]for_,rinbody.iterrows():namestr(r.iloc[0]).strip()ifnameinCONTRACT:unit,_,_CONTRACT[name]try:valfloat(r.iloc[1])except(ValueError,TypeError):continue# 解析失败跳过不填 0# 若导出件带了单位列第 3 列按其换算found_unitunitiflen(r)2:raw_unitstr(r.iloc[2])fCONV.get((name,norm_unit(raw_unit)))iffisnotNone:val*f rows.append({case_id:case_id,section:summary,parameter:name,value:val,unit:unit,source:report_export,})returnrowsdefmain():iflen(sys.argv)3:print(用法python parse_report.py export.xlsx case_0001)returnpath,case_idsys.argv[1],sys.argv[2]rowsparse_summary(path,case_id)dfpd.DataFrame(rows,columns[case_id,section,parameter,value,unit,source])outf{case_id}_results_long.csvdf.to_csv(out,indexFalse,encodingutf-8-sig)print(f解析完成{len(df)}条记录 -{out})ifnotdf.empty:print(df.to_string(indexFalse))if__name____main__:main()逐行剖析CONTRACT把规范名 → 单位/类型/是否允许缺失固化解析脚本据此校验而不是盲目信任导出件列名。CONV是显式换算表键是(规范名, 归一化单位)把Pa→kPa这类换算写成代码常量杜绝凭感觉估单位。norm_unit归一化单位写法W/m2·K与W/(m2·K)视为同一导出件单位栏写法可能不统一先归一化再查表。解析失败ValueError/TypeError时**continue跳过**而不是填 0这是 1.4 节三态缺失中解析失败态的处理——宁可缺、不可假。输出固定四列case_id/section/parameter/value/unit/source的长表source标注来源便于与对象模型取数合并时区分。sectionsummary本篇先做 summarydetailed 剖面1.2 节在下面代码 9-2 单独处理。代码 9-2对象模型取数 与报表结果合并# -*- coding: utf-8 -*- extract_results.py —— 对象模型取关键指标并与报表解析结果合并 用法python extract_results.py 【重要】所有 ... 标识符须替换为探测所得真实值。 importcsvimportpandasaspdfromdrive_caseimportsession# 复用第 07 篇会话PROGIDHTRIAutomationServer.ProgID本机枚举所得OP_LOAD打开案例的方法探测所得# 规范路径 - (本机真实标识符, 单位) —— 只列已探测确认的OUT_FIELDS{outputs.summary.overall_u:(真实标识符,W/(m2·K)),outputs.summary.shell_dP:(真实标识符,kPa),}defread_object_model(case_path,case_id):rows[]withsession(PROGID,300)as(app,_start):casegetattr(app,OP_LOAD)(case_path)fornorm,(ident,unit)inOUT_FIELDS.items():ifinident:continue# 未探测确认跳过不猜nodecaseforpartinident.split(.):nodegetattr(node,part)valgetattr(node,叶子属性名探测所得)rows.append({case_id:case_id,section:summary,parameter:norm.split(.)[-1],value:float(val),unit:unit,source:object_model,})returnrowsdefmain():ompd.DataFrame(read_object_model(case.htri,case_0001),columns[case_id,section,parameter,value,unit,source])try:rppd.read_csv(case_0001_results_long.csv,encodingutf-8-sig)exceptFileNotFoundError:rppd.DataFrame(columnsom.columns)mergedpd.concat([om,rp],ignore_indexTrue)# 交叉校验同一 caseparameter两来源应一致pivotmerged.pivot_table(index[case_id,parameter],columnssource,valuesvalue,aggfunclast)merged.to_csv(results_merged_long.csv,indexFalse,encodingutf-8-sig)print(f合并后{len(merged)}条记录 - results_merged_long.csv)ifreport_exportinpivotandobject_modelinpivot:diff(pivot[report_export]-pivot[object_model]).abs()pkpivot[pivot[report_export].notna()pivot[object_model].notna()]ifnotpk.empty:rel(pk[report_export]-pk[object_model]).abs()/pk[object_model].abs()print(两来源相对偏差应趋近 0)print(rel.round(6).to_string())if__name____main__:main()逐行剖析OUT_FIELDS里再次执行未探测确认就跳过if in ident把铁律 1 的护栏放到取数入口——取数同样不能用猜的标识符。source列区分object_model与report_export合并后仍可追溯每条记录来自哪条路。pivot_table(..., aggfunclast)把两来源并排这是交叉校验的最小实现——报表导出件与对象模型对同一指标应给出一致数值。相对偏差打印精度/一致性检查也是发现单位没对齐的有效手段若偏差恰为 1000 倍恭喜你抓到一个单位 bug。合并结果落results_merged_long.csv长表结构case_id/section/parameter/value/unit/source是后续第 10 篇落盘与第 17/19 篇分析的统一输入。三、常见报错与排查报错 3-1两来源数值差整数倍如 1000×。现象交叉校验偏差恰好 1000 或 1000000 倍。根因单位没对齐Pa vs kPaW/m²K 与其它。解法检查CONV换算表是否覆盖该指标与单位核对导出件的单位栏禁止用看起来像来推断。报错 3-2detailed 报表解析出来稀疏错位。现象一个 DataFrame 里大量 NaN、列对不上。根因detailed 是多组剖面的集合被强行读成一张二维表。解法按section, position, parameter, value长表格式分别解析每个剖面不要把不同剖面的横坐标混在一列。报错 3-3导出件列名是英文/中文混杂解析匹配不上。现象summary 解析结果为空。根因Xist 界面语言或导出模板变了列名/指标名本地化。解法locate_header支持多语言关键字参数/数值与Parameter/Value把契约名 → 各语言列名做成映射契约是稳定层。报错 3-4某一指标偶尔解析失败被静默跳过。现象某案例缺某指标但没报错。根因解析失败态被continue跳过设计如此。解法统计每批次的解析失败率若某指标缺失率异常高说明格式变了需要更新解析器。静默跳过要有监控否则会漏掉系统性错误。报错 3-5对象模型取值拿到的是上一次的结果。现象改了输入对象模型读数不变。根因在 run 完成前取数或复用了旧会话。解法取数严格排在运行完成后每案例独立会话第 07 篇纪律。报错 3-6只走报表导出件一条路漏掉单位错误。现象交付后才发现某指标差整数倍。根因没有交叉校验1.5 节纪律二。解法对关键指标同时用对象模型与报表两条路取数并比对相对偏差非 0 且为整数倍时优先查单位换算表。四、动手练习练习 1summary 解析对第 03 篇的导出件运行代码 9-1。判定生成*_results_long.csv含case_id/section/parameter/value/unit/source六列至少解析出 2 个契约内指标。练习 2单位换算构造一个壳侧压降以 Pa 给出的导出件运行解析。判定换算后数值与 kPa 版一致差值为 0且unit列仍是kPa。练习 3交叉校验对同一案例同时用对象模型与报表两条路取整体传热系数。判定两来源相对偏差 1%若偏差为整数倍说明单位未对齐需修复。练习 4detailed 长表取一份 detailed 剖面如沿程温度按section, position, parameter, value形成长表。判定长表行数 剖面点数 × 参数数无稀疏错位position 单调。五、小结与下一篇预告本篇把取数从读一个字段升级为一套取数工程两条路对象模型 / 报表导出件各有长短、应当并用summary 是键值表、detailed 是多组剖面不能一键转表多单位集是隐形地雷每个数值必须带单位或统一换算列契约比列名稳定。最终产出统一长表results_merged_long.csv并以交叉校验验证一致性。第 10 篇《结构化落盘》长表已经有了但怎么把它稳稳地写进磁盘/数据库、怎么管理案例矩阵的唯一键、怎么设计断点账本、怎么保证可复现是另一门功夫。我们会把 CSV/Parquet/JSON 元数据的取舍讲透并给出幂等的账本读写组件。本篇认知问题回显FAQQ1对象模型取数与报表导出件解析各自的长处与短处A对象模型取数精确可控、批量速度快适合在循环里取少量关键指标但依赖探测所得的真实标识符且审计留痕弱报表导出件解析凭官方版式的 Excel 文件、便于第三方复核与归档但批量速度慢、受版式随版本漂移影响。生产系统最优解是两者并用对象模型取关键指标入账本报表导出件做完整归档与交叉校验。Q2summary 与 detailed 报表结构上有什么本质差异ASummary reports 是一两页的总览结构接近键-值表整体传热系数、总压降、裕量、热负荷等标量适合逐行解析为宽表Detailed reports 是温度、压力、传热系数、热流等的局部剖面本质是多组剖面曲线的集合不能简单读成一张二维表正确做法是按section, position, parameter, value长表格式分别解析。Q3多单位集取数会带来什么后果怎么防AXist 支持 input/output 在多单位集含用户自定义集下动态显示同一量在不同单位集数值不同导出件用哪套单位取决于案例设置容易造成差 1000 倍的静默错误。防法是铁律级实践每个数值落盘必须带单位或全系列统一到 SI用显式换算表如 Pa→kPa 系数 0.001并在代码中注释来源绝不用数字看起来像猜单位。Q4为什么列契约比列名重要A列名会随版本漂移与界面语言变化而契约不变。列契约规定每列的规范名、单位、数据类型、是否允许缺失与来源对象模型/报表导出。解析脚本按契约校验列名只是契约到具体文件的映射当导出件改为英文列名时只改映射不动业务逻辑。Q5怎么把两条取数路的结果统一成一张长表A统一用case_id, section, parameter, value, unit, source六列长表source区分 object_model 与 report_export。合并后用pivot_table(index[case_id,parameter], columnssource, valuesvalue, aggfunclast)把两来源并排计算相对偏差做交叉校验应趋近 0若为整数倍则单位未对齐结果落results_merged_long.csv作为后续落盘与分析的统一输入。
分享:

看完干货,该让你的企业上线了

免费需求沟通 · 48 小时内出具建站方案 · 河南本地可上门