【设计模式】行为型-解释器模式

张开发
2026/4/3 17:26:02 15 分钟阅读
【设计模式】行为型-解释器模式
文章目录前言一、概念二、核心结构三、Java 代码实现加减运算解释器1. 抽象表达式2. 终结符数字3. 非终结符加法4. 非终结符减法5. 客户端构建语法树并解释四、优缺点优点缺点五、应用场景六、总结前言如果某个特定类型的问题频繁发生且可以用简单语法、规则表达式来表达我们就可以构建一个解释器让它解释这些“语法句子”从而解决问题。比如SQL 解析、正则表达式、规则引擎、公式计算、DSL 等。解释器模式就是为自定义语言、规则、表达式提供解释执行能力的行为型设计模式。一、概念解释器模式Interpreter Pattern是一种行为型设计模式核心思想给定一个语言定义它的文法的一种表示并定义一个解释器这个解释器使用该表示来解释语言中的句子。简单理解把语法规则拆成一个个表达式每个表达式负责解释自己组合起来就能解释一整句话。一句话总结自定义语法 → 拆成表达式 → 逐个解释。二、核心结构AbstractExpression抽象表达式定义解释接口interpret()。TerminalExpression终结符表达式最小单元不能再拆如数字、变量。NonTerminalExpression非终结符表达式组合多个表达式如 - * / 逻辑运算。Context上下文全局信息、变量、环境数据。Client构建语法树调用解释。三、Java 代码实现加减运算解释器实现一个最简单的数字 加法 减法解释器。1. 抽象表达式publicinterfaceExpression{intinterpret();}2. 终结符数字// 终结表达式数字publicclassNumberExpressionimplementsExpression{privateintnumber;publicNumberExpression(intnumber){this.numbernumber;}Overridepublicintinterpret(){returnnumber;}}3. 非终结符加法// 非终结加法publicclassAddExpressionimplementsExpression{privateExpressionleft;privateExpressionright;publicAddExpression(Expressionleft,Expressionright){this.leftleft;this.rightright;}Overridepublicintinterpret(){returnleft.interpret()right.interpret();}}4. 非终结符减法// 非终结减法publicclassSubExpressionimplementsExpression{privateExpressionleft;privateExpressionright;publicSubExpression(Expressionleft,Expressionright){this.leftleft;this.rightright;}Overridepublicintinterpret(){returnleft.interpret()-right.interpret();}}5. 客户端构建语法树并解释解释10 5 - 3publicclassClient{publicstaticvoidmain(String[]args){// 10 5 - 3Expressionnum10newNumberExpression(10);Expressionnum5newNumberExpression(5);Expressionnum3newNumberExpression(3);// 105ExpressionaddnewAddExpression(num10,num5);// (105)-3ExpressionsubnewSubExpression(add,num3);System.out.println(结果sub.interpret());}}输出结果12四、优缺点优点语法由类表示易扩展、易修改规则易于实现简单 DSL / 规则引擎符合开闭原则新增表达式只需加类缺点复杂文法会造成类爆炸效率低不适合复杂语法调试困难五、应用场景正则表达式引擎SQL 解析器规则引擎简单规则公式计算Excel 表达式配置文件解析自定义 DSL 脚本经典应用Java 正则Pattern/MatcherSpring EL 表达式MyBatis OGNLAviator 表达式引擎六、总结解释器模式 自定义语法 表达式拆分 递归解释核心每个规则对应一个表达式类结构抽象表达式 终结/非终结表达式 上下文适合简单语法、规则频繁变化的场景复杂语法请用专业工具ANTLR、JavaCC不要手写解释器

更多文章