Interpreter mode example of behavior mode

Review the design pattern today and see the interpreter pattern. Thinking of a problem I encountered before.

问题:前后端多条件的解析。
例:某字符串token开始于“a” 且包含“b” 或长度等于10

Previously, it was solved through three-party components. If you want to implement an extensible and easy-to-interact solution by yourself. I didn't think of a good way before.

In fact, it can be solved by encapsulating two layers in the interpreter mode.

But my interpreter example uses another simpler example as an example. The above is just a thought.

问题:波兰表示法。运算符末尾添加操作数的方式
例:1 2 + 代表1+2的运算。 3 4 + 5 - 6 + 代表3+4-5+6的运算

The interpreter generally consists of several parts.

1. Context (environment): encapsulates the global information of the interpreter, all specific interpreters need to access the Context.

2. AbstractExpression: an abstract class or interface. The interpretation method of the statement execution is implemented by all specific interpreters.

3. TerminalExpression (terminal expression). An interpreter class that implements operations related to grammar terminators. The terminal expression must be implemented or instantiated, because it signifies the end of the expression

4. NonTerminalExpression (non-terminal expression): a class that implements different rules or symbols of grammar. Every grammar should create a class.

Implementation code example:

1. Expression interface:

/**
 * 表达式接口
 */
public interface Expression {

    public float interpret();
}

2. Terminator expression. (In this example, a numeric value)

/**
 * 数值表达式
 */
public class NumberExpression implements Expression{


    private float number;

    public NumberExpression(float number){
        this.number = number;
    }

    @Override
    public float interpret() {
        return number;
    }
}

3. Non-terminal symbol expressions. In this example, the two rules of addition and subtraction are taken as examples

/**
 * 操作符解释器:加法
 */
public class PlusExpression implements Expression{


    Expression left;
    Expression right;
    public PlusExpression(Expression left, Expression right){

        this.left = left;
        this.right = right;
    }
    @Override
    public float interpret() {
        return this.left.interpret() + this.right.interpret();
    }
}
/**
 * 操作符解释器:减法
 */
public class MinusExpression implements Expression{


    Expression left;
    Expression right;
    public MinusExpression(Expression left, Expression right){

        this.left = left;
        this.right = right;
    }
    @Override
    public float interpret() {
        return this.left.interpret() - this.right.interpret();
    }
}

4. Write a piece of code to implement the syntax tree by creating a good class.

/**
 * 通过解释器类实现语法树
 */
public class Evaluator {

    public float evaluator(String expression){

        Stack<Expression> stack = new Stack<>();
        float result = 0;
        for (String token : expression.split(" ")){

            if(isOperator(token)){
                Expression exp = null;
                if(token.equals("+")){
                   exp = stack.push(new PlusExpression(stack.pop(), stack.pop()));
                }else if(token.equals("-")){
                   exp = stack.push(new MinusExpression(stack.pop(),stack.pop()));
                }

                if(exp != null){
                    result = exp.interpret();
                    stack.push(new NumberExpression(result));
                }
            }

            if(isNumber(token)){
                stack.push(new NumberExpression(Float.parseFloat(token)));
            }
        }
        return result;
    }

    private boolean isOperator(String token){
        if(token.equals("+") || token.equals("-"))
            return true;
        return false;
    }

    private boolean isNumber(String token){
        try {
            float v = Float.parseFloat(token);
            return true;
        }catch (Exception e){
            return false;
        }
    }

    public static void main(String[] args) {

        Evaluator evaluator = new Evaluator();
        System.out.println(evaluator.evaluator("2 3 +"));
        System.out.println(evaluator.evaluator("2 3 + 5 - 6 +"));
    }
}

A simple interpreter mode code is complete.

Guess you like

Origin blog.csdn.net/MrBack/article/details/106887429