解释器模式
GitHub代码链接
解释器模式(Interpreter Pattern)提供了评估语言和语法表达式的方式。
什么是解释器模式
解释器模式实现了一个表达式的接口,该接口解释一个特定的上下文。这种模式被用在SQL语句处理,符号解释引擎等。
解决的问题
给定一个语言,定义他的文法,并定义一个解释器,这个解释器使用该标识来解释语言中的句子。如果一种特定类型的问题发生的频率足够高,那么就值得将该问题的各个实例表述为一个简单语言中的句子,这样就可以构建一个解释器,解释器通过解析这些句子来解决该问题。
优点
- 可拓展性高,灵活
- 易于实现简单的文法
缺点
- 可使用场景少
- 对于复杂的文法较难维护
- 解释器模式会引起类膨胀
- 解释器模式采用递归调用的方法
代码实现
1. 创建语句的接口
//Expression 语句接口
type Expression interface {
Interpret(context string) bool
}
2. 创建终端语句类
//TerminalExpression 终端语句类
type TerminalExpression struct {
Data string
}
//NewTerminalExpression 实例化终端语句类
func NewTerminalExpression(data string) *TerminalExpression {
return &TerminalExpression{
Data: data,
}
}
//Interpret 终端语句类的解释器
func (te *TerminalExpression) Interpret(context string) bool {
if strings.Contains(context, te.Data) {
return true
}
return false
}
3. 创建逻辑语句类
//OrExpression 或语句类
type OrExpression struct {
Expr1 Expression
Expr2 Expression
}
//NewOrExpression 实例化或语句
func NewOrExpression(expr1, expr2 Expression) *OrExpression {
return &OrExpression{
Expr1: expr1,
Expr2: expr2,
}
}
//Interpret 解释器
func (oe *OrExpression) Interpret(context string) bool {
return oe.Expr1.Interpret(context) || oe.Expr2.Interpret(context)
}
//AndExpression 与语句类
type AndExpression struct {
Expr1 Expression
Expr2 Expression
}
//NewAndExpression 实例化与语句
func NewAndExpression(expr1, expr2 Expression) *AndExpression {
return &AndExpression{
Expr1: expr1,
Expr2: expr2,
}
}
//Interpret 解释器
func (ae *AndExpression) Interpret(context string) bool {
return ae.Expr1.Interpret(context) && ae.Expr2.Interpret(context)
}
4. 测试
func OrExpressionTest(t *testing.T) {
//规则,lee 和 wang 是男性
lee := NewTerminalExpression("Lee")
wang := NewTerminalExpression("Wang")
isMale := NewOrExpression(lee, wang)
fmt.Println("lee is male? ", isMale.Interpret("Lee"))
}
func AndExpressionTest(t *testing.T) {
//规则,yang是已婚女性
yang := NewTerminalExpression("Yang")
married := NewTerminalExpression("Married")
isMarried := NewAndExpression(yang, married)
fmt.Println("Yang is a married women? ", isMarried.Interpret("Married Yang"))
}
上一篇
下一篇
有疑问加站长微信联系(非本文作者)