Design Pattern

Interpreter Pattern

Clean Java-only production-ready implementation.


Given a language/grammar, interpret sentences in that language. Each grammar rule is represented as a class. The client builds an abstract syntax tree (AST) and evaluates it.

// ─── EXAMPLE 1 ──────────────────────────────────────────────────────────────
// WHAT WE ARE IMPLEMENTING:
// A boolean logic evaluator resolving expressions like 'x AND true' at
// runtime.
//
// WHERE THE INTERPRETER FITS IN:
// Expression is the Abstract Expression. Constant and Variable are Terminal
// Expressions. And is a Non-Terminal Expression (combining nodes).
// ────────────────────────────────────────────────────────────────────────────
// ─── EXAMPLE 1: BOOLEAN ALGEBRA EXPRESSION EVALUATOR ────────────────────────
import java.util.*;

interface Expression {
    boolean interpret(Map<String, Boolean> context);
}

class Constant implements Expression {
    private final boolean value;
    public Constant(boolean value) { this.value = value; }
    public boolean interpret(Map<String, Boolean> context) { return value; }
}

class Variable implements Expression {
    private final String name;
    public Variable(String name) { this.name = name; }
    public boolean interpret(Map<String, Boolean> context) {
        return context.getOrDefault(name, false);
    }
}

class And implements Expression {
    private final Expression left;
    private final Expression right;
    public And(Expression left, Expression right) {
        this.left = left;
        this.right = right;
    }
    public boolean interpret(Map<String, Boolean> context) {
        return left.interpret(context) && right.interpret(context);
    }
}

public class Main {
    public static void main(String[] args) {
        // Expression: x AND true
        Expression expr = new And(new Variable("x"), new Constant(true));
        
        Map<String, Boolean> context = new HashMap<>();
        context.put("x", true);
        
        System.out.println("Result: " + expr.interpret(context)); // Output: true
    }
}