应设计可携带上下文的CalculationException类继承RuntimeException,包含expression、contextSnapshot、stepTrace、nodePath字段,支持链式构建与运行时动态填充,并通过统一拦截器捕获底层异常、 enrich 上下文后抛出,同时提供结构化调试输出与内存安全控制。

在 Java 复杂计算引擎中,自定义 CalculationException 携带中间计算步骤数据,核心思路是:把关键上下文(如当前表达式、变量值、执行节点、堆栈路径等)作为字段封装进异常类,并支持链式构建或运行时动态填充。
设计可携带上下文的 CalculationException 类
继承 RuntimeException,添加字段记录计算过程中的关键信息:
-
expression:当前正在求值的表达式字符串(如
"a + b * c") -
contextSnapshot:快照式 Map(如
Map<string object></string>),保存计算到该点时各变量/参数的实际值 -
stepTrace:List
或自定义 StepRecord,记录已执行的原子步骤(如 "resolve 'a' → 5", "call function f(5) → null") -
nodePath:表示 AST 或计算图中的路径(如
["root", "add", "right", "multiply"]),便于定位失败位置
在计算过程中主动捕获并 enrich 异常
不要等到抛出时才收集数据;应在每层关键逻辑(如函数调用、表达式求值、类型转换)前/后,将上下文注入当前异常实例:
当用户要求为 Java 代码添加注释、修改注释、审查注释、整理注释格式,或要求按照代码注释规范处理 Java 文件时,使用本技能。本技能用于统一生成和维护 Java 类注释模板、按 Git 对比 release 判断版本号、补充每行代码上方中文块注释、调整注释空行规则,并保持 Java 文件 UTF-8 无 BOM 编码。典型触发场景包括:补充类注释、更新 @version、检查 @author 来源、整理行尾注释、把注释放到代码上一行、检查注释是否符合规范、构建前检查 Java 注释风格。
- 使用构造函数传入初始上下文,后续通过
withContext(...)或addStep(...)方法追加信息 - 在拦截器或计算节点基类中统一处理:捕获底层异常 → 新建
CalculationException→ 复制当前上下文 → 设置 cause → 抛出 - 示例:
try {
result = evaluator.eval(expr, context);
} catch (Exception e) {
throw new CalculationException("Evaluation failed", expr, context.snapshot(), e)
.addStep("evaluating: " + expr)
.atNode("AddNode#123");
}
支持结构化日志与调试输出
重写 toString() 或提供 toDebugReport() 方法,按层级组织信息,方便排查:
立即学习“Java免费学习笔记(深入)”;
- 第一部分:错误摘要(消息 + 原因)
- 第二部分:表达式与当前节点路径
- 第三部分:变量快照(只显示非 null / 非默认值项)
- 第四部分:执行轨迹(倒序列出最后 5 步,含时间戳或序号)
- 第五部分:原始异常堆栈(可选折叠)
避免过度序列化与内存泄漏
中间数据可能含大对象(如临时 DataFrame、大 Map),需注意:
- 对 snapshot 和 stepTrace 字段做浅拷贝或只存 toString() 或 ID,而非强引用原始对象
- 设置最大 step 数(如 20 条),超出则丢弃最早步骤
- 敏感字段(如用户 ID、密码)在加入异常前自动脱敏
- 考虑实现
Serializable时排除非必要字段(transient)

















