一、介绍
解释器是一种用的比较少的行为模式,其提供了一种解释语言的语法,或者表达式的方式。该模式定义了一个表达式的接口。
Demo地址:http://download.csdn.net/download/baopengjian/10011261
解释器是一种用的比较少的行为模式,其提供了一种解释语言的语法,或者表达式的方式。该模式定义了一个表达式的接口。
Demo地址:http://download.csdn.net/download/baopengjian/10011261
二、特点:
1、必须有一个抽象接口
2、构建语法树
2、构建语法树
三、 应用场景:
1、简单的语言需要解释执行而且可以将该语言中的语句表示一个抽象的语法树
1、简单的语言需要解释执行而且可以将该语言中的语句表示一个抽象的语法树
2、对于某个特定的领域出现的不断重复的问题,可以转换成一种语法规则下的语句
四、运用:
四、运用:
手机号码的验证
移动:134、135、136、137、138、139、150、151、157(TD)、158、159、187、188
联通:130、131、132、152、155、156、185、186
电信:133、153、180、189、(1349卫通)
正则表达式"^((13[0-9])|(15[^4,\\D])|(18[0,5-9]))\\d{8}$"
移动:134、135、136、137、138、139、150、151、157(TD)、158、159、187、188
联通:130、131、132、152、155、156、185、186
电信:133、153、180、189、(1349卫通)
正则表达式"^((13[0-9])|(15[^4,\\D])|(18[0,5-9]))\\d{8}$"
五、优缺点
优点:
每个语法都要产生一个非终结符表达式,语法规则比较复杂时,就可能产生大量的类文件,为维护带来了非常多的麻烦。
缺点:
解释器模式采用递归调用方法
每个非终结符表达式只关心与自己有关的表达式,每个表达式需要知道最终的结果,必须一层一层地剥茧,无论是面向过程的语言还是面向对象的语言,递归都是在必要条件下使用的,它导致调试非常复杂。想想看,如果要排查一个语法错误,我们是不是要一个一个断点的调试下去,直到最小的语法单元。
解释器模式由于使用了大量的循环和递归,效率是个不容忽视的问题,特别是用于解析复杂、冗长的语法时,效率是难以忍受的。
五、Demo
计算3*5*7/3
优点:
每个语法都要产生一个非终结符表达式,语法规则比较复杂时,就可能产生大量的类文件,为维护带来了非常多的麻烦。
缺点:
解释器模式采用递归调用方法
每个非终结符表达式只关心与自己有关的表达式,每个表达式需要知道最终的结果,必须一层一层地剥茧,无论是面向过程的语言还是面向对象的语言,递归都是在必要条件下使用的,它导致调试非常复杂。想想看,如果要排查一个语法错误,我们是不是要一个一个断点的调试下去,直到最小的语法单元。
解释器模式由于使用了大量的循环和递归,效率是个不容忽视的问题,特别是用于解析复杂、冗长的语法时,效率是难以忍受的。
五、Demo
计算3*5*7/3
1、定义抽象接口
public interface Node { int interpret(); }
2、定义两个实现:
//单纯的数字
public class ValueNode implements Node { private int value; public ValueNode(int value){ this.value = value; } @Override public int interpret() { return value; } }
//带运算符的
public abstract class SymbolNode implements Node { protected Node left; protected Node right; public SymbolNode(Node left,Node right){ this.left = left; this.right = right; } }3、根据具体乘或除实现
除法:
public class DivNode extends SymbolNode{ public DivNode(Node left, Node right) { super(left, right); } @Override public int interpret() { return left.interpret()/right.interpret(); } }
乘法:
public class MulNode extends SymbolNode{ public MulNode(Node left, Node right) { super(left, right); } @Override public int interpret() { return left.interpret()*right.interpret(); } }4、定义计算规则
public class Caculator { public int build(String statement) { Node left = null; Node right = null; Node lastNode = null; String[] statements = statement.split(" "); for (int i = 0; i < statements.length; i++) { if ("*".equalsIgnoreCase(statements[i])) { left = lastNode; int val = Integer.parseInt(statements[++i]); right = new ValueNode(val); lastNode = new MulNode(left, right); } else if ("/".equalsIgnoreCase(statements[i])) { left = lastNode; int val = Integer.parseInt(statements[++i]); right = new ValueNode(val); lastNode = new DivNode(left, right); } else { lastNode = new ValueNode(Integer.parseInt(statements[i])); } } return lastNode.interpret(); } }5 计算
public static void main(String[]args){ String contentString="3 * 5 * 7"; Caculator caculator=new Caculator(); int result=caculator.build(contentString); }
6 拓展很方便,比如添加一个取余运算
public class ModNode extends SymbolNode {
public ModNode(Node left, Node right) {
super(left, right);
}
@Override
public int interpret() {
return left.interpret() % right.interpret();
}
}
在计算规则中添加取余的逻辑即可
public class Caculator {
public int build(String statement) {
Node left = null;
Node right = null;
Node lastNode = null;
String[] statements = statement.split(" ");
for (int i = 0; i < statements.length; i++) {
if ("*".equalsIgnoreCase(statements[i])) {
left = lastNode;
int val = Integer.parseInt(statements[++i]);
right = new ValueNode(val);
lastNode = new MulNode(left, right);
} else if ("/".equalsIgnoreCase(statements[i])) {
left = lastNode;
int val = Integer.parseInt(statements[++i]);
right = new ValueNode(val);
lastNode = new DivNode(left, right);
} else if ("%".equalsIgnoreCase(statements[i])) {
left = lastNode;
int val = Integer.parseInt(statements[++i]);
right = new ValueNode(val);
lastNode = new ModNode(left, right);
} else {
lastNode = new ValueNode(Integer.parseInt(statements[i]));
}
}
return lastNode.interpret();
}
在计算规则中添加取余的逻辑即可