解釋器模式字面意思,也即解釋某些內容的含義,這種設計模式是實際開發中最不容易用到的,比如SQL決議,符號處理引擎,會用到解釋器模式,屬于更底層的開發人員才會用到的設計模式,
本文就以解釋器模式的概念、角色和簡單的例子說明解釋器模式,讀者對這部分內容了解即可,
一、概念
解釋器模式是指給定一門語言,定義它的文法的一種表示(如:加減乘除運算式和正則運算式等),然后再定義一個解釋器,該解釋器用來解釋我們的文法表示(運算式),
解釋器模式的結構與組合模式相似,不過其包含的組成元素比組合模式多,而且組合模式是物件結構型模式,而解釋器模式是類行為型模式,
解釋器模式中包含四個角色:
-
抽象解釋器(Abstract Expression)角色:定義解釋器的介面,約定解釋器的解釋操作,主要包含解釋方法 interpret(),
-
終結符解釋器(Terminal Expression)角色:是抽象運算式的子類,用來實作文法中與終結符相關的操作,文法中的每一個終結符都有一個具體終結運算式與之相對應,
-
非終結符解釋器(Nonterminal Expression)角色:也是抽象運算式的子類,用來實作文法中與非終結符相關的操作,文法中的每條規則都對應于一個非終結符運算式,
-
環境(Context)角色:通常包含各個解釋器需要的資料或是公共的功能,一般用來傳遞被所有解釋器共享的資料,后面的解釋器可以從這里獲取這些值,
解釋器模式類結構圖如圖所示:

二、實作
接下來針對四個角色分別定義他們的實作,
抽象解釋器:
/**
* 宣告一個抽象的解釋操作,這個介面為抽象語法樹中所有的節點所共享
* @author tcy
* @Date 29-08-2022
*/
public abstract class AbstractExpression {
public abstract boolean interpret(String info);
}
非終結符運算式:
/**
* 非終結符運算式,為文法中的非終結符實作解釋操作,對文法中每一條規則R1、R2...Rn都需要一個具體的非終結符運算式類
* @author tcy
* @Date 29-08-2022
*/
public class NonTerminalExpression extends AbstractExpression{
private AbstractExpression address=null;
private AbstractExpression name=null;
private AbstractExpression id=null;
public NonTerminalExpression(AbstractExpression address, AbstractExpression name, AbstractExpression id) {
this.address = address;
this.name = name;
this.id = id;
}
@Override
public boolean interpret(String info) {
String s[]=info.split("-");
return address.interpret(s[0])&&name.interpret(s[1])&&id.interpret(s[2]);
}
}
終結符運算式:
**
* 實作與文法中的終結符相關聯的解釋操作,文法中每一個終結符都有一個具體終結運算式與之相對應
* @author tcy
* @Date 29-08-2022
*/
public class TerminalExpression extends AbstractExpression{
private Set<String> set =new HashSet<String>();
public TerminalExpression(String[] data)
{
for(int i=0; i<data.length;i++)
set.add(data[i]);
}
@Override
public boolean interpret(String info) {
if(set.contains(info))
{
return true;
}
return false;
}
}
背景關系環境:
/**
* 背景關系環境
* @author tcy
* @Date 29-08-2022
*/
public class Context {
private String[] shuzis={"1","2","3","4","5","6","7","8","9","0"};
private String[] xiaoxiezimus={"a","b","c","d","e","f","g","h","i","j","k","l"};
private String[] daxiezimus={"A","B","C","D","E","F","G"};
private AbstractExpression infomation;
public Context()
{
AbstractExpression shuzi=new TerminalExpression(shuzis);
AbstractExpression xiaoxiezimu=new TerminalExpression(xiaoxiezimus);
AbstractExpression daxiezimu=new TerminalExpression(daxiezimus);
infomation=new NonTerminalExpression(shuzi,xiaoxiezimu,daxiezimu);
}
public void jieshi(String info)
{
boolean ok=infomation.interpret(info);
if(ok) System.out.println("正確! ["+info+"] 滿足 [單個數字-單個小寫-單個大寫] 的條件");
else System.out.println("錯誤! ["+info+"] 不滿足 [單個數字-單個小寫-單個大寫] 的條件");
}
}
客戶端:
/**
* @author tcy
* @Date 29-08-2022
*/
public class Client {
public static void main(String[] args) {
Context people=new Context();
people.jieshi("2-a-A");
people.jieshi("11-A-5");
people.jieshi("你-好-吖");
people.jieshi("2aA");
}
}
以上為解釋器模式的簡單案例,讀者可以拉取代碼到本地進行學習,
三、應用場景
解釋器模式在實際的軟體開發中使用比較少,因為它會引起效率、性能以及維護等問題,
在JDK中的正則運算式中的Pattern類和Spring里面的ExpressionParse介面使用的是解釋器模式的思想,
當一個語言需要解釋執行,并且語言中的句子可以表示為一個抽象語法樹的時候,如 XML 檔案解釋,整體來說還是一種應用較少的設計模式,
已經連續更新了數十篇設計模式博客,推薦你結合學習,
一、設計模式概述
二、設計模式之工廠方法和抽象工廠
三、設計模式之單例和原型
四、設計模式之建造者模式
五、設計模式之代理模式
六、設計模式之配接器模式
七、設計模式之橋接模式
八、設計模式之組合模式
九、設計模式之裝飾器模式
十、設計模式之外觀模式
十一、外觀模式之享元模式
十二、設計模式之責任鏈模式
十三、設計模式之命令模式
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/504766.html
標籤:設計模式
上一篇:過濾陣列問題
下一篇:設計模式之解釋器模式
