go-pattern-examples/behavior/08_interpreter/interpreter.go

148 lines
3.1 KiB
Go
Raw Permalink Normal View History

2020-04-21 17:50:21 +03:00
package interpreter
import (
2020-05-05 09:44:57 +03:00
"fmt"
2020-04-21 17:50:21 +03:00
"strings"
)
2020-05-05 09:44:57 +03:00
//用会议交流的例子,规则如下:
2020-05-04 19:01:23 +03:00
// A表示左边发言者B表示右边发言者
// A "->" B 表示 A说B听,此时B不能发言。
// A "<-" B 表示 B说A听,此时B不能发言。
// A "<->" B 表示 A 和 B 可以自由发言。
2020-05-05 09:44:57 +03:00
//IActionInterpret 解释器
2020-05-04 19:01:23 +03:00
type IActionInterpret interface {
Interpret()
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//SpeakerUnit 每个参与动作的单元都是,会议发言者
type SpeakerUnit struct {
Name string
CanSpeak bool //每个参会者有两种基本的行为,发言或者安静
}
2020-05-04 19:01:23 +03:00
2020-05-05 09:44:57 +03:00
//Interpret 解释自己的基本行为
func (s *SpeakerUnit) Interpret() {
if s.CanSpeak {
fmt.Println("i'm", s.Name, "im speaking")
return
}
fmt.Println("i'm", s.Name, "already silent")
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//LeftSpeakAction A "->" B 表示 A说B听,此时B不能发言。
type LeftSpeakAction struct {
leftSpeaker, rightSpeaker IActionInterpret
}
//Interpret 解释执行
func (l *LeftSpeakAction) Interpret() {
l.leftSpeaker.Interpret()
l.rightSpeaker.Interpret()
2020-05-04 19:01:23 +03:00
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//RightSpeakAction A "<-" B 表示 B说A听,此时B不能发言。
type RightSpeakAction struct {
leftSpeaker, rightSpeaker IActionInterpret
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//Interpret 解释执行
func (r *RightSpeakAction) Interpret() {
r.leftSpeaker.Interpret()
r.rightSpeaker.Interpret()
}
2020-05-04 19:01:23 +03:00
2020-05-05 09:44:57 +03:00
//BothSpeakAction : A "<->" B 表示 A 和 B 可以自由发言。
type BothSpeakAction struct {
leftSpeaker, rightSpeaker IActionInterpret
}
2020-05-04 19:01:23 +03:00
2020-05-05 09:44:57 +03:00
//Interpret 解释执行
func (b *BothSpeakAction) Interpret() {
b.leftSpeaker.Interpret()
b.rightSpeaker.Interpret()
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//SignParser 我们自己的DSL解析器
type SignParser struct {
actionUnits []string //要解析的内容
result IActionInterpret //上一个也是解释器单元
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//解析 ->
func (s *SignParser) newLeftSpeakAction() IActionInterpret {
left := &SpeakerUnit{
Name: s.actionUnits[0],
CanSpeak: true,
}
right := &SpeakerUnit{
Name: s.actionUnits[2],
}
return &LeftSpeakAction{
leftSpeaker: left,
rightSpeaker: right,
}
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//解析 <-
func (s *SignParser) newRightSpeakAction() IActionInterpret {
left := &SpeakerUnit{
Name: s.actionUnits[0],
}
right := &SpeakerUnit{
Name: s.actionUnits[2],
CanSpeak: true,
}
return &LeftSpeakAction{
leftSpeaker: left,
rightSpeaker: right,
}
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//解析 <->
func (s *SignParser) newBothSpeakAction() IActionInterpret {
2020-04-21 17:50:21 +03:00
2020-05-05 09:44:57 +03:00
left := &SpeakerUnit{
Name: s.actionUnits[0],
CanSpeak: true,
}
right := &SpeakerUnit{
Name: s.actionUnits[2],
CanSpeak: true,
}
return &LeftSpeakAction{
leftSpeaker: left,
rightSpeaker: right,
}
}
//Parse 标识解析器进行解析exp就是要解释的内容
func (s *SignParser) Parse(exp string) {
2020-04-21 17:50:21 +03:00
2020-05-05 09:44:57 +03:00
s.actionUnits = strings.Split(exp, " ") //单元分割符
switch s.actionUnits[1] {
case "->":
s.result = s.newLeftSpeakAction()
case "<-":
s.result = s.newRightSpeakAction()
case "<->":
s.result = s.newBothSpeakAction()
default:
fmt.Println("some error raised")
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
2020-04-21 17:50:21 +03:00
}
2020-05-05 09:44:57 +03:00
//Result 就是两边正确执行了动作
func (s *SignParser) Result() {
2020-04-21 17:50:21 +03:00
2020-05-05 09:44:57 +03:00
s.result.Interpret()
2020-04-21 17:50:21 +03:00
2020-05-05 09:44:57 +03:00
}