A brief introduction to interpreter mode

1. What is interpreter mode

The interpreter pattern (Interperter) is one of the behavioral design patterns. It is a scheme of parsing according to a specified syntax. It is defined as: Given a language ,define a representation for its grammar along with an interpreter that uses the representation to Interpret sentences in the language (given a language, define a grammar rule and provide a corresponding interpreter to interpret the statements in the grammar) The interpreter pattern is rarely used in real development, and most of the time we use the interpreter pattern implementation directly, such as regular expressions, cron expressions, and so on.

2. Service scenarios

The Java language has been designed to implement many of the most common expressions we use in our everyday needs, but there are some obscure mathematical expressions that he does not directly support in the JDK. For example, we learned about factorials in high school math.

Factorial is a mathematical term invented by Christian Kramp (1760 ~ 1826) in 1808.

The factorial of a positive integer (factorial) is the product of all positive integers less than or equal to that number, and 0 factorial is 1. The factorial of the natural number n is written as n! . This notation was introduced by Keith Karman in 1808. That is, n! = 1 x 2 x 3 x… * n (n – 1). Factorial can also be defined recursively: 0! = 1, n! =(n-1)! X n.

So today we’ll walk you through the interpreter pattern in everyday use by implementing a factorial calculator.

Second, the implementation of interpreter mode

1. Design idea

Before we proceed to code implementation, we first need to develop a simple calculation flow chart:Let’s analyze how many roles are involved in the process:

  1. AbstractExpression: concrete interpretation tasks are handed over to subclasses, and concrete interpreters are done by terminal and non-terminal expressions.
  2. TerminalExpression: The logical processing of non-operational elements of a statement.
  3. NonterminalExpression: responsible for the logical processing of operator-related elements in an operation instruction.
  4. Context: Is responsible for storing operation instructions (expressions).

Ok, parse to see the code implementation:

2. Code implementation of interpreter mode

1. Let’s create an abstract interpreter

public interface Expression {
	Integer interpret(a);
}
Copy the code

2. Let’s first implement a terminal expression

public class NumberExpression implements Expression {

	private Integer number;

	public NumberExpression(Integer number) {
		super(a);this.number = number;
	}

	@Override
	public Integer interpret(a) {
		// TODO Auto-generated method stub
		returnnumber; }}Copy the code

3. Then we implement a non-terminal expression

public class FactorialExpression implements Expression {
	
	private Expression expression;
	private Integer result; 

	public FactorialExpression(Expression expression) {
		super(a);this.expression = expression;
	}

	@Override
	public Integer interpret(a) {
		result = expression.interpret();
		
		for (int i = result-1; i > 1; i--) {
			result *= i;
		}
		returnresult; }}Copy the code

4. Then let’s make a factorial calculator

public class Calculator {

	private Expression expression;

	public Calculator(String expStr) {
		Stack<Expression> stack = new Stack<>();
		char[] charArray = expStr.toCharArray();
		for (char c : charArray) {
			if ("!".equals(String.valueOf(c))) {
				Expression pop = stack.pop();
				expression = new FactorialExpression(pop);
			} else {
				NumberExpression numberExpression = newNumberExpression(Character.getNumericValue(c)); stack.push(numberExpression); }}}public Integer execute(a) {
		returnexpression.interpret(); }}Copy the code

Test code:

public class Client {

	public static void main(String[] args) {
		String expStr = "Eight!";
		Calculator calculator = new Calculator(expStr);
		Integer result = calculator.execute();
		System.out.println(expStr + The operation result of "is :"+ result); }}Copy the code

Test results:

3. Class diagram design of interpreter pattern

Summary of interpreter model

1. Features of the interpreter pattern

Advantages:

  1. It is highly extensible

Disadvantages:

  1. It causes the class to swell
  2. Increase the complexity of the system
  3. Low efficiency

2. Usage scenarios of interpreter mode

  1. A statement that needs to be interpreted can be represented as an abstract syntax tree
  2. Resend the problem that occurred

3. Pay attention to

Please do not use the interpreter mode in important modules, which will cause the later maintenance is very difficult. In the project, we can try to use scripting languages (such as shell, JRuby, Groovy, etc.) to make up for the deficiency of Java language design.

Four, conclusion

Today’s proxy mode explanation is all over, the related code of the design mode has been included in Gitee, you can take it directly if you need it:

Gitee.com/xiaolong-ob…

If you have any questions, you are welcome to leave a message in the comment section or send a private message to the blogger, who will answer them for you in the first time. The code word is not easy, feel the harvest of friends remember to pay attention to the blogger, do not be white whoring monster oh ~ blogger here wish you can be promoted in the New Year, to the peak of life!