设计模式之-解释器模式
定义:
解释器模式(Interpreter Pattern) :定义语言的文法,并且建立一个解释器来解释该语言中的句子,这里的“语言”意思是使用规定格式和语法的代码,它是一种类行为型模式。
解释器模式参与者
- Context:包含解释器之外的一些全局信息。
- AbstractExpression:抽象表达式,声明一个抽象的解释操作,这个接口为抽象语法树中所有的节点共享。
- TerminalExpression:终结符表达式,实现与文法中的终结符相关联的解释操作。
- NonterminalExpression:非终结符表达式,为文法中的非终结符实现解释操作。对文法中的每一条规则R1,R2......Rn,都需要一个具体的非终结符表达式类。
解释器模式基本代码
Context类:
namespace InterpreterPattern.BasicStructure { class Context { public string Input { get; set; } public string Output { get; set; } } }
AbstractExpression类:
namespace InterpreterPattern.BasicStructure { abstract class AbstractExpression { public abstract void Interpret(Context context); } }
TerminalExpression类:
namespace InterpreterPattern.BasicStructure { class TerminalExpression : AbstractExpression { public override void Interpret(Context context) { Console.WriteLine("终端解释器"); } } }
NonterminalExpression类:
namespace InterpreterPattern.BasicStructure { class NonterminalExpression : AbstractExpression { public override void Interpret(Context context) { Console.WriteLine("非终端解释器"); } } }
客户端调用代码:
static void Main(string[] args) { try { {//BasicStructure Context context = new Context(); IList<AbstractExpression> list = new List<AbstractExpression>(); list.Add(new TerminalExpression()); list.Add(new NonterminalExpression()); list.Add(new TerminalExpression()); list.Add(new TerminalExpression()); foreach (var item in list) { item.Interpret(context); } } } catch (Exception ex) { Console.WriteLine(ex.Message); } Console.ReadKey(); }
结果如下:
用解释器模式实现英文翻译
场景模拟:作为一个学渣级的存在,读书时没有学好英文,现在碰到英文时常常需要借助一些翻译工具。
ChineseEnglishDict(环境)类——Context类
namespace InterpreterPattern.SituationSimulation { /// <summary> /// 环境类 /// </summary> class ChineseEnglishDict { private Dictionary<string, string> _dictory = new Dictionary<string, string>(); public ChineseEnglishDict() { _dictory.Add("this", "这"); _dictory.Add("is", "是"); _dictory.Add("an", "一个"); _dictory.Add("apple", "苹果"); } public string GetEnglish(string value) { return _dictory[value.ToLower()]; } } }
TranslateExpression(翻译抽象)类——AbstractExpression类
namespace InterpreterPattern.SituationSimulation { /// <summary> /// 翻译抽象类 /// </summary> abstract class TranslateExpression { public abstract string Interpret(ChineseEnglishDict context); } }
WordExpression(单词翻译)类——NonterminalExpression类
namespace InterpreterPattern.SituationSimulation { /// <summary> /// 单词翻译类 /// </summary> class WordExpression : TranslateExpression { private string _value; public WordExpression(string value) { this._value = value; } public override string Interpret(ChineseEnglishDict dict) { return new StringBuilder().Append(dict.GetEnglish(_value)).ToString(); } } }
SymbolExpression(符号翻译)类——TerminalExpression类
namespace InterpreterPattern.SituationSimulation { /// <summary> /// 符号翻译类 /// </summary> class SymbolExpression : TranslateExpression { private string _value; public SymbolExpression(string value) { this._value = value; } public override string Interpret(ChineseEnglishDict dict) { switch (_value) { case ".": return new StringBuilder().Append("。").ToString(); default: return _value; } } } }
客户端调用代码:
static void Main(string[] args) { try { {//SituationSimulation IList<TranslateExpression> list = new List<TranslateExpression>(); string english = "This is an apple."; var elements = english.Split(new char[] { '.' }, StringSplitOptions.RemoveEmptyEntries); foreach (var element in elements) { var words = element.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); foreach (var word in words) { list.Add(new WordExpression(word)); } list.Add(new SymbolExpression(".")); } ChineseEnglishDict dict = new ChineseEnglishDict(); string result = ""; foreach (var item in list) { result += item.Interpret(dict); } Console.WriteLine(english + "翻译后:" + result); } } catch (Exception ex) { Console.WriteLine(ex.Message); } Console.ReadKey(); }
结果如下:
优点:
解释器模式的优点
- 解释器是一个简单的语法分析工具,它最显著的优点就是扩展性,修改语法规则只需要修改相应的非终结符就可以了,若扩展语法,只需要增加非终结符类就可以了。
缺点:
解释器模式的缺点
- 解释器模式会引起类的膨胀,每个语法都需要产生一个非终结符表达式,语法规则比较复杂时,就可能产生大量的类文件,为维护带来非常多的麻烦。
- 执行效率较低。
- 对于复杂的文法比较难维护。
适用环境:
根据代理模式的使用目的,常见的代理模式有以下几种类型:
- 可以将一个需要解释执行的语言中的句子表示为一个抽象语法树。
- 一些重复出现的问题可以用一种简单的语言来进行表达。
- 文法较为简单。
- 效率不是关键问题。
总结:
- 在解释器模式中由于语法是由很多类表示的,所以可扩展性强。
- 然解释器的可扩展性强,但是如果语法规则的数目太大的时候,该模式可能就会变得异常复杂。所以解释器模式适用于文法较为简单的。
- 解释器模式可以处理脚本语言和编程语言。常用于解决某一特定类型的问题频繁发生情况。