在不更改这个类的前提下,更改这个类中方法所能执行的逻辑。即根据外部环境(传入的访问者Visitor不同)更改这个类所能执行的行为。
将数据结构与数据操作分离,实现稳定的数据结构和易变的操作耦合问题。
image.png image.png- Visitor中定义了对被访问者Element的操作,ObjectStruct作为容器存储了Element队列并且开放了Visitor的访问。每个Element都有调用动态visitor方法的accept
package main
import "fmt"
type Visitor interface {
VisitConcreteElementA(*ConcreteElementA)
VisitConcreteElementB(*ConcreteElementB)
}
type ConcreteVisitor1 struct {
}
func (v *ConcreteVisitor1) VisitConcreteElementA(ele *ConcreteElementA) {
ele.Operation()
}
func (v *ConcreteVisitor1) VisitConcreteElementB(ele *ConcreteElementB) {
ele.Operation()
}
type Element interface {
accept(Visitor)
}
type ConcreteElementA struct {
}
func (e *ConcreteElementA) accept(visitor Visitor) {
visitor.VisitConcreteElementA(e)
}
func (e *ConcreteElementA) Operation() {
fmt.Println("eleA operation")
}
type ConcreteElementB struct {
}
func (e *ConcreteElementB) accept(visitor Visitor) {
visitor.VisitConcreteElementB(e)
}
func (e *ConcreteElementB) Operation() {
fmt.Println("eleB operation")
}
type ObjectStructure struct {
col []Element
}
func (o *ObjectStructure) accept(visitor Visitor) {
for _, e := range o.col {
e.accept(visitor)
}
}
func (o *ObjectStructure) addElement(ele ...Element) {
for _, e := range ele {
o.col = append(o.col, e)
}
}
func main() {
os := new(ObjectStructure)
eleA := new(ConcreteElementA)
eleB := new(ConcreteElementB)
os.addElement(eleA, eleB)
visitor := new(ConcreteVisitor1)
os.accept(visitor)
}
网友评论