继续我们的《设计模式》的学习课程!今天我要讲的是解释器——Interpreter模式,因为昨天同事刚讲了这个模式,趁着脑子里面还有印象,赶紧通过写这篇文章来巩固下!
定义:定义语言的文法,并且建立一个解释器来解释该语言中的句子。它属于类的行为模式。这里的语言意思是使用规定格式和语法的代码。
意图:抽取语法中最基本的功能,以便于进行代码重用
类图:
涉及的角色有:
1、Expression :表达式,是一个接口或抽象类;
2、TerminalExpression :终结符表达式角色,是表达式的一个子类或实现类
3、NonterminalOneExpression : 非终结符表达式角色,也是表达式的一个子类或实现类
4、Context :上下文环境
示例如下:
package service;
import impl.Context;
import java.math.BigDecimal;
/*
* 抽象表达式
*/
public interface Expression
{
public BigDecimal interpreter(Context con);
}
package impl;
import java.math.BigDecimal;
import java.util.Hashtable;
import service.Expression;
/*
* 语法上下文
*/
public class Context
{
private Hashtable table;
public Context()
{
this.table = new Hashtable<Expression,BigDecimal>();
}
public void addValue(Expression pression,BigDecimal value)
{
this.table.put(pression, value);
}
public BigDecimal getValue(Expression pression)
{
BigDecimal value = (BigDecimal) this.table.get(pression);
return value;
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
/*
* 变量(终结符表达式)
*/
public class Varial implements Expression
{
public BigDecimal interpreter(Context con)
{
BigDecimal value = con.getValue(this);
return value;
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
/*
* 常量
*/
public class Constant implements Expression {
private BigDecimal data;
public Constant(BigDecimal value)
{
this.data = value;
}
@Override
public BigDecimal interpreter(Context con)
{
return data;
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
public class AddExpression implements Expression {
private Expression left;
private Expression right;
@Override
public BigDecimal interpreter(Context con)
{
return left.interpreter(con).add(right.interpreter(con));
}
public AddExpression(Expression left,Expression right)
{
this.left = left;
this.right = right;
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
public class DivExpression implements Expression {
private Expression left;
private Expression right;
@Override
public BigDecimal interpreter(Context con)
{
//两个BigDecimal对象相除时,如果除不尽,则会报错,所以要进行舍入
return left.interpreter(con).divide(right.interpreter(con),2,BigDecimal.ROUND_HALF_UP);
}
public DivExpression(Expression left,Expression right)
{
this.left = left;
this.right = right;
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
public class MultipExpression implements Expression {
private Expression left;
private Expression right;
@Override
public BigDecimal interpreter(Context con)
{
return left.interpreter(con).multiply(right.interpreter(con));
}
public MultipExpression(Expression left,Expression right)
{
this.left = left;
this.right = right;
}
}
package client;
import impl.AddExpression;
import impl.Constant;
import impl.Context;
import impl.DivExpression;
import impl.MultipExpression;
import impl.SubtracExpression;
import impl.Varial;
import java.math.BigDecimal;
import service.Expression;
public class TestInterpreter {
/**
* @param args
*/
public static void main(String[] args)
{
//(a*b*b)/(a+b-3)
Context ctx = new Context();
Expression a = new Varial();
Expression b = new Varial();
Expression c = new Constant(new BigDecimal("3"));
ctx.addValue(a, new BigDecimal("6"));
ctx.addValue(b, new BigDecimal("8"));
ctx.addValue(c, c.interpreter(null));
Expression rs = new DivExpression(new MultipExpression(a, new MultipExpression(b, b)), new SubtracExpression(new AddExpression(a, b), c));
BigDecimal result = rs.interpreter(ctx);
System.out.println("计算结果:"+result);
}
}
package impl;
import java.math.BigDecimal;
import service.Expression;
public class SubtracExpression implements Expression
{
private Expression left;
private Expression right;
@Override
public BigDecimal interpreter(Context con)
{
return left.interpreter(con).subtract(right.interpreter(con));
}
public SubtracExpression(Expression left,Expression right)
{
this.left = left;
this.right = right;
}
}
总结:
解释器以我个人的理解的话,首先它使用的场合不是很多,它适合于解释某种语言或规则。在解释这些规则时要
注意查找规律性的东西,把最基本的功能抽取出来,然后才能利用!