
首先,引物
解释器模式描述了如何构建简单的语言解释器,主要用于面向对象的语言开发
在编译器中;在实际应用中,我们很少会遇到构建语言语法的情况.
尽管您很少使用此模式,但仍然可以从中得到启发.
第二,定义和结构
解释器模式的定义如下: 定义语言的语法,并构建解释器以解释该语言的句子.
它属于类的行为模式. 这里的语言表示使用指定格式和语法的代码.
正如GOF的书中指出的那样: 如果某种特定类型的问题发生得足够频繁,则可能有必要进行更改
每个问题实例都用一种简单的语言表达为一个句子. 这样,您可以构建解释器. 口译员可以工作.
解释这些句子以解决问题. 当语法简单且效率不是关键问题时,此方法最有效-
应用解释器模式的环境.
让我们看看是什么构成了神秘的解释器模式.
1)抽象表达作用: 声明抽象解释操作. 该界面适用于所有具体的表达角色(抽象语言
方法树中的节点).
什么是抽象语法树? “ java和模式”中给出的解释是: 抽象语法树的每个节点都是
表示一条语句,并且可以在每个节点上执行解释方法. 这种解释方法的执行就是这样
The
语句被解释. 因为每个语句都代表该语句进行解释. 由于每个语句代表一个共同点
一个问题的例子,因此在每个节点上的解释操作代表问题实例的答案.
2)终止符表达角色: 特定表达.
a)实现与语法中的终端字符相关的解释操作
b)句子中的每个终止符都需要一个类的实例才能与其对应
3)非终端表达角色: 特定表达.
a)语法R :: = R1R2 ... Rn中的每个规则都需要一个非结尾的带字符.
b)为R1到Rn中的每个符号维护一个抽象表达角色的实例变量
c)为了实现解释操作,解释通常以递归方式调用代表那些从R1到Rn的对象的解释操作
4)上下文(环境)角色: 包含解释器之外的一些全局信息.
5)客户角色:
a)构造(或给定)抽象语法树,以语法定义的语言表示特定的句子
b)调用解释操作

放置解释器结构的类图,该类图也来自GOF.

呵呵,每个角色都被赋予了详细的职责,并且在类图中给出了五个角色之间的关系. 这个
实现它不是很困难. 这是一个简单的例子. 我希望加深您对口译模式的理解.
三个例子
让我们以加,减,乘和除为例. 实现思想来自“ Java和模式”中的示例. 对于每个字符
功能是根据上述规范实现的.
//上下文(环境)角色,使用HashMap存储对应于变量的值
类上下文{
私有地图valueMap =新的HashMap();
public void addValue(变量x,int y){
Integer yi = new Integer(y);
valueMap.put(x,yi);
}
public int LookupValue(变量x){
int i =((整数)valueMap.get(x)). intValue();
返回我;
}
}
//抽象表达角色解释器模式,也可以使用接口实现
抽象类表达式{
public abstract int解释(上下文相关);
}
//终端表达角色
class常量扩展表达式{
private int i;
公共常量(int i){
this.i = i;
}
public int interpret(Context con){

返回我;
}
}
class变量扩展了表达式{
public int interpret(Context con){
//这是调用解释方法的Variable对象
返回con.LookupValue(this);
}
}
//非终止符表达角色
class Add扩展了表达式{
左,右私人表达;
公共添加(左表达式,右表达式){
this.left = left;
this.right = right;
}
public int interpret(Context con){
返回左解释(con)+右解释(con);
}
}
类减法扩展表达式{
左解释器模式,右私人表达;
公共减法(左表达式,右表达式){
this.left = left;
this.right = right;
}
public int interpret(Context con){
返回左. 解释(con)-右. 解释(con);
}
}

Class Multiply扩展表达式{
左,右私人表达;
公共乘法(左表达式,右表达式){
this.left = left;
this.right = right;
}
public int interpret(Context con){
返回左. 解释(con)*右. 解释(con);
}
}
类划分扩展了表达式{
左,右私人表达;
公共部门(左表达,右表达){
this.left = left;
this.right = right;
}
public int interpret(Context con){
尝试{
左转解释(con)/右转解释(con);
}捕获(ArithmeticException ae){
System.out.println(“除数为0!”);
返回-11111;
}
}
}
//测试程序,计算(a * b)/(a-b + 2)
公共课程测试
{
私人静态表达式ex;
私有静态上下文骗局;

public static void main(字符串[] args){
con =新上下文();
//设置变量和常量
变量a =新变量();
变量b =新变量();
常数c =新常数(2);
//为变量分配值
con.addValue(a,5);
con.addValue(b,7);
//操作,我们分析并构建句子的结构
ex =新除法(新乘(a,b),新加(新减(a,b),c));
System.out.println(“操作结果是: ” + ex.interpret(con));
}
}
解释器模式没有说明如何创建抽象语法树,因此,如上所述,其实现可以有所不同
我们直接在Test中提供它,当然还有更好,更的实现方式.
对于终结者,GOF建议使用Flyweight模式共享其副本,因为它们会反复出现.
但是考虑到Flyweight模式的局限性,我建议您在系统中重复终止符足够多的情况下使用它.
考虑Flyweight模式.
四个优点和缺点
解释器模式提供了一种执行语法的简单方法,并且很容易修改或扩展语法. 通用系统
许多课程
使用类似的语法. 您可以使用解释器,而不是为每个规则实现解释器. 还有
不同的规则由解释器中的不同类实现,因此可以轻松添加新的语法规则.
但是对于复杂的语法来说,解释器模式很难维护. 想象每个规则应该对应一个处理类.
此外,这些类还必须递归调用抽象表达式角色. 交织在一起是多么糟糕.
啊!
V. 摘要
因此,您应该对解释器模式有一个大致的了解. 由于缺少这种模式下的案例,因此本书
文本的大部分要点直接来自GOF的原始作品.
本文来自电脑杂谈,转载请注明本文网址:
http://www.pc-fly.com/a/jisuanjixue/article-159997-1.html
冗余过分
杨洋加油