设计模式-解释器模式

作者持续关注 WPS二次开发专题系列,持续为大家带来更多有价值的WPS开发技术细节,如果能够帮助到您,请帮忙来个一键三连,更多问题请联系我(QQ:250325397)

定义

解释器模式(Interpreter Pattern)提供了评估语言的语法或表达式的方式,它属于行为型模式。这种模式实现了一个表达式接口,该接口解释一个特定的上下文。这种模式被用在 SQL 解析、符号处理引擎等。

特点

给定一个语言,定义它的文法表示,并定义一个解释器,这个解释器使用该标识来解释语言中的句子。

使用场景

编译器、运算表达式计算。

优缺点

(1) 优点
    • 可扩展性比较好,灵活。
    • 增加了新的解释表达式的方式。
    • 易于实现简单文法。
(2) 缺点
    • 可利用场景比较少。
    • 对于复杂的文法比较难维护。
    • 解释器模式会引起类膨胀。
    • 解释器模式采用递归调用方法。

模式结构

    • 定义一个抽象表达式(Expression)接口,它包含了解释方法 interpret(String info)。
    • 定义一个终结符表达式(Terminal Expression)类,它用集合(Set)类来保存满足条件的城市或人,并实现抽象表达式接口中的解释方法 interpret(Stringinfo),用来判断被分析的字符串是否是集合中的终结符。
    • 定义一个非终结符表达式(AndExpressicm)类,它也是抽象表达式的子类,它包含满足条件的城市的终结符表达式对象和满足条件的人员的终结符表达式对象,并实现 interpret(String info) 方法,用来判断被分析的字符串是否是满足条件的城市中的满足条件的人员。
    • 最后,定义一个环境(Context)类,它包含解释器需要的数据,完成对终结符表达式的初始化,并定义一个方法 freeRide(String info) 调用表达式对象的解释方法来对被分析的字符串进行解释。

具体实现

接口和实现

/**
 * 抽象表达式类
 */
interface Expression {

    /**
     * 解释
     */
    boolean interpret(String info);
}

/**
 * 非终结符表达式类
 */
class AndExpression implements Expression {
    private Expression city = null;
    private Expression person = null;

    public AndExpression(Expression city, Expression person) {
        this.city = city;
        this.person = person;
    }

    public boolean interpret(String info) {
        String s[] = info.split("的");
        return city.interpret(s[0]) && person.interpret(s[1]);
    }
}

/**
 * 终结符表达式类
 */
class TerminalExpression implements Expression {
    private Set<String> set = new HashSet<>();

    public TerminalExpression(String[] data) {
        set.addAll(Arrays.asList(data));
    }

    public boolean interpret(String info) {
        if (set.contains(info)) {
            return true;
        }
        return false;
    }
}

环境类

/**
 * 环境类
 */
class Context {
    private String[] cities = {"武汉"};
    private String[] persons = {"老人", "妇女", "儿童"};
    private Expression cityPerson;

    public Context() {
        Expression city = new TerminalExpression(cities);
        Expression person = new TerminalExpression(persons);
        cityPerson = new AndExpression(city, person);
    }

    public void freeRide(String info) {
        boolean ok = cityPerson.interpret(info);
        if (ok) System.out.println("您是" + info + ",您本次乘车免费!");
        else System.out.println(info + ",您不是免费人员,本次乘车扣费2元!");
    }
}

具体使用

/**
 * 状态模式
 * 介绍链接:https://www.kdocs.cn/l/ct3ki9na5JMo
    <pre>
        文法规则
        <expression> ::= <city>的<person>
        <city> ::= 武汉
        <person> ::= 老人|妇女|儿童
    </pre>
*/
public class App {
    public static void main(String[] args) {
        Context bus = new Context();
        bus.freeRide("武汉的老人");
        bus.freeRide("武汉的年轻人");
        bus.freeRide("深圳的妇女");
        bus.freeRide("深圳的儿童");
    }
}

实际应用

  1. 存款利息计算(设置好计算规则)
相关推荐
morris1313 分钟前
【SpringBoot】Xss的常见攻击方式与防御手段
java·spring boot·xss·csp
七星静香28 分钟前
laravel chunkById 分块查询 使用时的问题
java·前端·laravel
Jacob程序员28 分钟前
java导出word文件(手绘)
java·开发语言·word
ZHOUPUYU29 分钟前
IntelliJ IDEA超详细下载安装教程(附安装包)
java·ide·intellij-idea
stewie632 分钟前
在IDEA中使用Git
java·git
Elaine2023911 小时前
06 网络编程基础
java·网络
G丶AEOM1 小时前
分布式——BASE理论
java·分布式·八股
落落鱼20131 小时前
tp接口 入口文件 500 错误原因
java·开发语言
想要打 Acm 的小周同学呀1 小时前
LRU缓存算法
java·算法·缓存
镰刀出海1 小时前
Recyclerview缓存原理
java·开发语言·缓存·recyclerview·android面试