-
Notifications
You must be signed in to change notification settings - Fork 46
/
main.go
110 lines (86 loc) · 2.52 KB
/
main.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
// 访问者模式 visitor pattern.
// 该模式用于将数据结构和操作进行分离,同样用于分离操作的还有策略模式(strategy pattern),但两者存在侧重点的不同.
// 访问者模式侧重于扩展访问的方法类型,是为了对某一个类及其子类的访问方式进行扩展,允许增加更多不同的访问者,但不宜增加更多的Host.
// 以下以实体A(仅有玩家、NPC、物体三类)被访问(查看信息、发起挑战等,此处可扩展)的过程
package main
import "log"
// 如果这里有更多的新类型Host需要扩展,则不宜使用访问者模式
type Host interface {
Accept(Visitor)
}
type PlayerHost struct {
Name string
Level int
}
func (p PlayerHost)Accept(v Visitor){
v.VisitPlayer(p)
}
type NPCHost struct {
Name string
IsImmortal bool
}
func (n NPCHost)Accept(v Visitor){
v.VisitNPC(n)
}
type ObjectHost struct {
Name string
Price int
}
func (o ObjectHost)Accept(v Visitor){
v.VisitObject(o)
}
type Visitor interface {
VisitPlayer(PlayerHost)
VisitNPC(NPCHost)
VisitObject(ObjectHost)
}
// 访问者允许有不同类型的访问者
// 仅查看信息的访问者
type InfoVisitor struct {}
func (InfoVisitor) VisitPlayer(p PlayerHost) {
log.Printf("Player -> Name:%s ,Level:%d\n" ,p.Name ,p.Level)
}
func (InfoVisitor) VisitNPC(n NPCHost) {
log.Printf("NPC -> Name:%s ,Immortal:%v\n" ,n.Name ,n.IsImmortal)
}
func (InfoVisitor) VisitObject(o ObjectHost) {
log.Printf("Object -> Name:%s ,Price:%d\n" ,o.Name ,o.Price)
}
// 发起攻击的访问者
type AggressiveVisitor struct {}
func (AggressiveVisitor) VisitPlayer(p PlayerHost) {
log.Printf("Attack %s\n" ,p.Name)
}
func (AggressiveVisitor) VisitNPC(n NPCHost) {
log.Printf("Attack NPC %s\n" ,n.Name)
}
func (AggressiveVisitor) VisitObject(o ObjectHost) {
log.Printf("Unsupported target %s\n" ,o.Name)
}
func main(){
infoVst := InfoVisitor{}
agrVst := AggressiveVisitor{}
pA := PlayerHost{"icg" ,1}
pB := PlayerHost{"sz" ,2}
npc := NPCHost{"nyn" ,true}
obj := ObjectHost{"cake" ,19}
hostList := []Host{pA ,npc ,obj ,pB}
for _ ,v := range hostList{
v.Accept(infoVst)
}
println()
for _ ,v := range hostList{
v.Accept(agrVst)
}
/*
output:
2019/05/04 10:00:49 Player -> Name:icg ,Level:1
2019/05/04 10:00:49 NPC -> Name:nyn ,Immortal:true
2019/05/04 10:00:49 Object -> Name:cake ,Price:19
2019/05/04 10:00:49 Player -> Name:sz ,Level:2
2019/05/04 10:00:49 Attack icg
2019/05/04 10:00:49 Attack NPC nyn
2019/05/04 10:00:49 Unsupported target cake
2019/05/04 10:00:49 Attack sz
*/
}