设计模式之美
王争
前 Google 工程师,《数据结构与算法之美》专栏作者
123426 人已学习
新⼈⾸单¥98
登录后,你可以任选6讲全文学习
课程目录
已完结/共 113 讲
设计模式与范式:行为型 (18讲)
设计模式之美
15
15
1.0x
00:00/00:00
登录|注册

72 | 解释器模式:如何设计实现一个自定义接口告警规则功能?

支持括号的重构
项目经历
拆分解析逻辑
灵活性
小类解析
拆分解析工作
信息传递
广义语言
解释器
语法规则
课堂讨论
代码实现
实现思路
应用范围
定义
解释器模式

该思维导图由 AI 生成,仅供参考

上一节课,我们学习了命令模式。命令模式将请求封装成对象,方便作为函数参数传递和赋值给变量。它主要的应用场景是给命令的执行附加功能,换句话说,就是控制命令的执行,比如,排队、异步、延迟执行命令、给命令执行记录日志、撤销重做命令等等。总体上来讲,命令模式的应用范围并不广。
今天,我们来学习解释器模式,它用来描述如何构建一个简单的“语言”解释器。比起命令模式,解释器模式更加小众,只在一些特定的领域会被用到,比如编译器、规则引擎、正则表达式。所以,解释器模式也不是我们学习的重点,你稍微了解一下就可以了。
话不多说,让我们正式开始今天的学习吧!

解释器模式的原理和实现

解释器模式的英文翻译是 Interpreter Design Pattern。在 GoF 的《设计模式》一书中,它是这样定义的:
Interpreter pattern is used to defines a grammatical representation for a language and provides an interpreter to deal with this grammar.
翻译成中文就是:解释器模式为某个语言定义它的语法(或者叫文法)表示,并定义一个解释器用来处理这个语法。
确认放弃笔记?
放弃后所记笔记将不保留。
新功能上线,你的历史笔记已初始化为私密笔记,是否一键批量公开?
批量公开的笔记不会为你同步至部落
公开
同步至部落
取消
完成
0/2000
荧光笔
直线
曲线
笔记
复制
AI
  • 深入了解
  • 翻译
    • 英语
    • 中文简体
    • 中文繁体
    • 法语
    • 德语
    • 日语
    • 韩语
    • 俄语
    • 西班牙语
    • 阿拉伯语
  • 解释
  • 总结

解释器模式是一种用于定义语言的语法表示并提供解释器来处理这个语法的设计模式。本文通过生活和编程的例子解释了解释器模式的概念,并展示了一个简单的加减乘除计算语言的语法规则及相应的代码实现。作者讨论了如何利用解释器模式将语法解析的工作拆分到各个小类中,以避免大而全的解析类,并对代码进行了重构,将解析工作拆分成五个独立的单元,分别对数字和四种运算符进行解析。接着,文章提供了一个实际的例子,展示了如何实现一个自定义接口告警规则功能,将自定义的告警规则看作一种特殊“语言”的语法规则,并实现一个解释器,能够根据规则,针对用户输入的数据,判断是否触发告警。通过这些例子,读者可以了解解释器模式的原理和实现方式,以及如何应用解释器模式来处理复杂的语法规则。解释器模式的代码实现比较灵活,没有固定的模板,其核心思想是将语法解析的工作拆分到各个小类中,以此来避免大而全的解析类。

仅可试看部分内容,如需阅读全部内容,请付费购买文章所属专栏
《设计模式之美》
新⼈⾸单¥98
立即购买
登录 后留言

全部留言(48)

  • 最新
  • 精选
  • 花儿少年
    类似于规则引擎是不是也是个解释器,只不过是个复杂很多的解释器

    作者回复: 是的 没错

    2020-04-27
    10
  • Panmax
    第二个代码示例中的代码段: if (operator.equals("+")) { combinedExp = new AdditionExpression(exp1, exp2); } else if (operator.equals("-")) { combinedExp = new AdditionExpression(exp1, exp2); } else if (operator.equals("*")) { combinedExp = new AdditionExpression(exp1, exp2); } else if (operator.equals("/")) { combinedExp = new AdditionExpression(exp1, exp2); } 应改为: if (operator.equals("+")) { combinedExp = new AdditionExpression(exp1, exp2); } else if (operator.equals("-")) { combinedExp = new SubstractionExpression(exp1, exp2); } else if (operator.equals("*")) { combinedExp = new MultiplicationExpression(exp1, exp2); } else if (operator.equals("/")) { combinedExp = new DivisionExpression(exp1, exp2); }
    2020-04-18
    8
    68
  • LiuHu
    SpEL(Spring Expression Language ) 就是典型的解释器模式实现。 在项目中实现简单的自动化规则过滤器,就是将过滤器配置翻译成 SpEL 表达式执行的
    2020-05-05
    40
  • javaadu
    我是做风控技术的,发现这个模式对我理解规则引擎的设计很有帮助
    2020-04-29
    20
  • 迷羊
    因为做的是数据类型的项目,就是根据自定义的SQL来创建API以供可以通过http形式直接调用,项目中就是用Druid来解析SQL的,用的就是解释器模式,SQL语句中的每个字符对应一个表达式。
    2020-04-18
    3
    16
  • Ken张云忠
    Java中注解处理器做的就是解释的功能,以及前端编译时的语法分析、语义分析,后端编译时生成的中间表达式,用来触发更多优化,优化的处理可以理解为高效的解释,最终生成机器可以执行的汇编指令。
    2020-04-17
    2
    11
  • kylexy_0817
    ES中的各种分词器
    2020-04-25
    10
  • 辣么大
    关于问题一,使用过。偏向科研,自定义一门语言,然后通过语法解析器分析读入。 例如使用RDDL(Relational Domain Definition Language)关系领域定义语言描述马尔可夫决策过程。 domain prop_dbn { requirements = { reward-deterministic }; pvariables { p : { state-fluent, bool, default = false }; q : { state-fluent, bool, default = false }; r : { state-fluent, bool, default = false }; a : { action-fluent, bool, default = false }; }; cpfs { // Some standard Bernoulli conditional probability tables p' = if (p ^ r) then Bernoulli(.9) else Bernoulli(.3); q' = if (q ^ r) then Bernoulli(.9) else if (a) then Bernoulli(.3) else Bernoulli(.8); // KronDelta is like a DiracDelta, but for discrete data (boolean or int) r' = if (~q) then KronDelta(r) else KronDelta(r <=> q); }; // A boolean functions as a 0/1 integer when a numerical value is needed reward = p + q - r; // a boolean functions as a 0/1 integer when a numerical value is needed } instance inst_dbn { domain = prop_dbn; init-state { p = true; // could also just say 'p' by itself q = false; // default so unnecessary, could also say '~q' by itself r; // same as r = true }; max-nondef-actions = 1; horizon = 20; discount = 0.9; }
    2020-04-17
    10
  • 鲨鱼辣椒
    定时任务中的cron表达式
    2020-05-20
    8
  • test
    加括号的话,要加一个ExpressionManager,在manager里面用括号把表达式划分为几段,再根据表达式间是 与 还是 或 来添加最上面那一层的表达式
    2020-04-17
    1
    7
收起评论
显示
设置
留言
48
收藏
沉浸
阅读
分享
手机端
快捷键
回顶部