运维锅总详解设计模式

本首先简介23种设计模式,然后用Go语言实现这23种设计模式进行举例分析。希望对您理解这些设计模式有所帮助!

一、设计模式简介

设计模式是软件设计中用于解决常见设计问题的一套最佳实践。它们不是代码片段,而是解决特定问题的通用方案。设计模式分为三大类:创建型模式、结构型模式和行为型模式。

创建型模式

创建型模式关注对象的创建过程。它们使得系统独立于对象的创建、组合和表示。常见的创建型模式有:

  1. 单例模式 (Singleton):确保一个类只有一个实例,并提供一个全局访问点。
  2. 工厂方法模式 (Factory Method):定义一个创建对象的接口,但让子类决定实例化哪一个类。
  3. 抽象工厂模式 (Abstract Factory):提供一个接口,用于创建相关或依赖对象的家族,而无需明确指定具体类。
  4. 建造者模式 (Builder):将一个复杂对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。
  5. 原型模式 (Prototype):通过复制现有的实例来创建新的对象,而不是通过实例化类。

结构型模式

结构型模式关注类和对象的组合。它们帮助确保系统结构的灵活性和效率。常见的结构型模式有:

  1. 适配器模式 (Adapter):将一个类的接口转换成客户希望的另一个接口,使原本不兼容的类可以一起工作。
  2. 桥接模式 (Bridge):将抽象部分与它的实现部分分离,使它们可以独立变化。
  3. 组合模式 (Composite):将对象组合成树形结构以表示“部分-整体”的层次结构,使得客户可以一致地处理单个对象和对象组合。
  4. 装饰模式 (Decorator):动态地给对象添加一些额外的职责,比生成子类更灵活。
  5. 外观模式 (Facade):为子系统中的一组接口提供一个一致的界面,使得子系统更容易使用。
  6. 享元模式 (Flyweight):通过共享尽可能多的细节来支持大量细粒度对象的高效共享。
  7. 代理模式 (Proxy):为其他对象提供一个代理以控制对这个对象的访问。

行为型模式

行为型模式关注对象之间的交互方式及职责划分。它们有助于使系统中的对象更容易通信和交互。常见的行为型模式有:

  1. 责任链模式 (Chain of Responsibility):将请求的发送者和接收者解耦,使多个对象都有机会处理这个请求。
  2. 命令模式 (Command):将一个请求封装为一个对象,从而使您可以用不同的请求对客户进行参数化。
  3. 解释器模式 (Interpreter):为语言创建解释器,定义语言的文法,并建立一个解释器来解释这些文法。
  4. 迭代器模式 (Iterator):提供一种方法顺序访问一个聚合对象中的各个元素,而无需暴露其内部表示。
  5. 中介者模式 (Mediator):用一个中介对象来封装一系列对象的交互。
  6. 备忘录模式 (Memento):在不破坏封装性的前提下,捕获并外部化一个对象的内部状态,以便以后恢复它。
  7. 观察者模式 (Observer):定义对象间的一种一对多的依赖关系,使得每当一个对象改变状态,则所有依赖于它的对象都会得到通知并被自动更新。
  8. 状态模式 (State):允许对象在其内部状态改变时改变其行为。
  9. 策略模式 (Strategy):定义一系列算法,把每一个算法封装起来,并且使它们可以互换。
  10. 模板方法模式 (Template Method):定义一个操作中的算法骨架,而将一些步骤延迟到子类中。
  11. 访问者模式 (Visitor):表示一个作用于某对象结构中的各元素的操作。它使您可以在不改变各元素的类的前提下定义作用于这些元素的新操作。

这些设计模式在实际应用中可以大大提高代码的可维护性和可重用性。了解并掌握这些模式对于设计健壮、灵活的软件系统是非常重要的。

二、Go语言实现23总设计模式

好的,我们重新从头开始,依次实现所有的设计模式。每个设计模式会有Go代码示例、Mermaid图和详细说明。

创建型模式(5种)

1. 单例模式 (Singleton)

单例模式确保一个类只有一个实例,并提供一个全局访问点。

Go代码示例
package mainimport ("fmt""sync"
)// Singleton 结构体
type Singleton struct{}var instance *Singleton
var once sync.Once// GetInstance 获取单例实例
func GetInstance() *Singleton {once.Do(func() {instance = &Singleton{}})return instance
}func main() {s1 := GetInstance()s2 := GetInstance()if s1 == s2 {fmt.Println("两个实例是相同的")} else {fmt.Println("两个实例是不同的")}
}
Mermaid图
Singleton
-Singleton instance
-sync.Once once
+GetInstance() : Singleton
2. 工厂方法模式 (Factory Method)

工厂方法模式定义一个创建对象的接口,但让子类决定实例化哪一个类。

Go代码示例
package mainimport "fmt"// 操作接口
type Operation interface {Perform(a, b int) int
}// 加法结构体
type Add struct{}// 加法实现
func (Add) Perform(a, b int) int {return a + b
}// 工厂方法
func getOperation(opType string) Operation {switch opType {case "add":return Add{}default:return nil}
}func main() {op := getOperation("add")if op != nil {result := op.Perform(3, 4)fmt.Println("结果:", result)} else {fmt.Println("无效的操作类型")}
}
Mermaid图
«interface»
Operation
+Perform(int, int) : int
Add
+Perform(int, int) : int
Factory
+getOperation(string) : Operation
3. 抽象工厂模式 (Abstract Factory)

抽象工厂模式提供一个接口,用于创建相关或依赖对象的家族,而无需明确指定具体类。

Go代码示例
package mainimport "fmt"// 抽象产品A
type AbstractProductA interface {UseA()
}// 抽象产品B
type AbstractProductB interface {UseB()
}// 具体产品A1
type ProductA1 struct{}func (p *ProductA1) UseA() {fmt.Println("使用产品A1")
}// 具体产品B1
type ProductB1 struct{}func (p *ProductB1) UseB() {fmt.Println("使用产品B1")
}// 抽象工厂
type AbstractFactory interface {CreateProductA() AbstractProductACreateProductB() AbstractProductB
}// 具体工厂1
type Factory1 struct{}func (f *Factory1) CreateProductA() AbstractProductA {return &ProductA1{}
}func (f *Factory1) CreateProductB() AbstractProductB {return &ProductB1{}
}func main() {factory := &Factory1{}productA := factory.CreateProductA()productB := factory.CreateProductB()productA.UseA()productB.UseB()
}
Mermaid图
«interface»
AbstractProductA
+UseA()
«interface»
AbstractProductB
+UseB()
ProductA1
+UseA()
ProductB1
+UseB()
«interface»
AbstractFactory
+CreateProductA() : AbstractProductA
+CreateProductB() : AbstractProductB
Factory1
+CreateProductA() : AbstractProductA
+CreateProductB() : AbstractProductB
4. 建造者模式 (Builder)

建造者模式将一个复杂对象的构建过程与其表示分离,使得同样的构建过程可以创建不同的表示。

Go代码示例
package mainimport "fmt"// 产品
type Product struct {Part1 stringPart2 string
}// 建造者接口
type Builder interface {BuildPart1()BuildPart2()GetResult() Product
}// 具体建造者
type ConcreteBuilder struct {product Product
}func (b *ConcreteBuilder) BuildPart1() {b.product.Part1 = "Part1"
}func (b *ConcreteBuilder) BuildPart2() {b.product.Part2 = "Part2"
}func (b *ConcreteBuilder) GetResult() Product {return b.product
}// 指挥者
type Director struct {builder Builder
}func (d *Director) Construct() {d.builder.BuildPart1()d.builder.BuildPart2()
}func main() {builder := &ConcreteBuilder{}director := &Director{builder: builder}director.Construct()product := builder.GetResult()fmt.Println("Product:", product)
}
Mermaid图
Product
+string Part1
+string Part2
«interface»
Builder
+BuildPart1()
+BuildPart2()
+GetResult() : Product
ConcreteBuilder
+Product product
+BuildPart1()
+BuildPart2()
+GetResult() : Product
Director
+Builder builder
+Construct()
5. 原型模式 (Prototype)

原型模式通过复制现有的实例来创建新的对象,而不是通过实例化类。

Go代码示例
package mainimport "fmt"// 原型接口
type Prototype interface {Clone() Prototype
}// 具体原型
type ConcretePrototype struct {field string
}func (p *ConcretePrototype) Clone() Prototype {return &ConcretePrototype{field: p.field}
}func main() {prototype := &ConcretePrototype{field: "value"}clone := prototype.Clone()fmt.Println("Prototype field:", prototype.field)fmt.Println("Clone field:", clone.(*ConcretePrototype).field)
}
Mermaid图
«interface»
Prototype
+Clone() : Prototype
ConcretePrototype
+string field
+Clone() : Prototype

结构型模式(7种)

6. 适配器模式 (Adapter)

适配器模式将一个类的接口转换成客户希望的另一个接口,使原本不兼容的类可以一起工作。

Go代码示例
package mainimport "fmt"// 旧接口
type OldPrinter interface {PrintOld(s string) string
}// 旧实现
type MyOldPrinter struct{}func (p *MyOldPrinter) PrintOld(s string) string {return "Old Printer: " + s
}// 新接口
type NewPrinter interface {PrintNew(s string) string
}// 适配器
type PrinterAdapter struct {OldPrinter
}func (p *PrinterAdapter) PrintNew(s string) string {return p.PrintOld(s)
}func main() {oldPrinter := &MyOldPrinter{}adapter := &PrinterAdapter{OldPrinter: oldPrinter}msg := adapter.PrintNew("Hello, World!")fmt.Println(msg)
}
Mermaid图
«interface»
OldPrinter
+PrintOld(string) : string
MyOldPrinter
+PrintOld(string) : string
«interface»
NewPrinter
+PrintNew(string) : string
PrinterAdapter
-OldPrinter oldPrinter
+PrintNew(string) : string
7. 桥接模式 (Bridge)

桥接模式将抽象部分与它的实现部分分离,使它们可以独立变化。

Go代码示例
package mainimport "fmt"// 实现接口
type Implementor interface {OperationImpl() string
}// 具体实现A
type ConcreteImplementorA struct{}func (c *ConcreteImplementorA) OperationImpl() string {return "具体实现A"
}// 具体实现B
type ConcreteImplementorB struct{}func (c *ConcreteImplementorB) OperationImpl() string {return "具体实现B"
}// 抽象
type Abstraction struct {implementor Implementor
}func (a *Abstraction) Operation() {fmt.Println(a.implementor.OperationImpl())
}// 精确抽象A
type RefinedAbstractionA struct {Abstraction
}func main() {implementorA := &ConcreteImplementorA{}implementorB := &ConcreteImplementorB{}abstractionA := &Abstraction{implementor: implementorA}abstractionB := &Abstraction{implementor: implementorB}abstractionA.Operation()abstractionB.Operation()
}
Mermaid图
«interface»
Implementor
+OperationImpl() : string
ConcreteImplementorA
+OperationImpl() : string
ConcreteImplementorB
+OperationImpl() : string
Abstraction
+Implementor implementor
+Operation()
RefinedAbstractionA
8. 组合模式 (Composite)

组合模式将对象组合成树形结构以表示“部分-整体”的层次结构,使客户端对单个对象和组合对象的使用具有一致性。

Go代码示例
package mainimport "fmt"// 组件接口
type Component interface {Operation()
}// 叶子节点
type Leaf struct {name string
}func (l *Leaf) Operation() {fmt.Println("Leaf", l.name, "Operation")
}// 组合节点
type Composite struct {children []Component
}func (c *Composite) Add(child Component) {c.children = append(c.children, child)
}func (c *Composite) Operation() {for _, child := range c.children {child.Operation()}
}func main() {leaf1 := &Leaf{name: "A"}leaf2 := &Leaf{name: "B"}composite := &Composite{}composite.Add(leaf1)composite.Add(leaf2)composite.Operation()
}
Mermaid图
«interface»
Component
+Operation()
Leaf
+string name
+Operation()
Composite
+[]Component children
+Add(Component)
+Operation()
9. 装饰模式 (Decorator)

装饰模式动态地给对象添加一些职责,通过创建一个包装对象来包裹真实对象。

Go代码示例
package mainimport "fmt"// 组件接口
type Component interface {Operation()
}// 具体组件
type ConcreteComponent struct{}func (c *ConcreteComponent) Operation() {fmt.Println("具体组件操作")
}// 装饰器
type Decorator struct {component Component
}func (d *Decorator) SetComponent(component Component) {d.component = component
}func (d *Decorator) Operation() {if d.component != nil {d.component.Operation()}
}// 具体装饰器A
type ConcreteDecoratorA struct {Decorator
}func (c *ConcreteDecoratorA) Operation() {c.Decorator.Operation()fmt.Println("具体装饰器A操作")
}// 具体装饰器B
type ConcreteDecoratorB struct {Decorator
}func (c *ConcreteDecoratorB) Operation() {c.Decorator.Operation()fmt.Println("具体装饰器B操作")
}func main() {component := &ConcreteComponent{}decoratorA := &ConcreteDecoratorA{}decoratorB := &ConcreteDecoratorB{}decoratorA.SetComponent(component)decoratorB.SetComponent(decoratorA)decoratorB.Operation()
}
Mermaid图
«interface»
Component
+Operation()
ConcreteComponent
+Operation()
Decorator
-Component component
+SetComponent(Component)
+Operation()
ConcreteDecoratorA
+Operation()
ConcreteDecoratorB
+Operation()
10. 外观模式 (Facade)

外观模式提供了一个统一的接口,用来访问子系统中的一群接口,使得子系统更容易使用。

Go代码示例
package mainimport "fmt"// 子系统A
type SubsystemA struct{}func (s *SubsystemA) OperationA() {fmt.Println("子系统A操作")
}// 子系统B
type SubsystemB struct{}func (s *SubsystemB) OperationB() {fmt.Println("子系统B操作")
}// 外观
type Facade struct {subsystemA *SubsystemAsubsystemB *SubsystemB
}func (f *Facade) Operation() {f.subsystemA.OperationA()f.subsystemB.OperationB()
}func main() {facade := &Facade{subsystemA: &SubsystemA{},subsystemB: &SubsystemB{},}facade.Operation()
}
Mermaid图
SubsystemA
+OperationA()
SubsystemB
+OperationB()
Facade
+SubsystemA subsystemA
+SubsystemB subsystemB
+Operation()
11. 享元模式 (Flyweight)

享元模式通过共享技术来有效地支持大量细粒度对象的复用。

Go代码示例
package mainimport ("fmt"
)// 享元接口
type Flyweight interface {Operation(extrinsicState string)
}// 具体享元
type ConcreteFlyweight struct {intrinsicState string
}func (f *ConcreteFlyweight) Operation(extrinsicState string) {fmt.Println("Intrinsic State =", f.intrinsicState, "Extrinsic State =", extrinsicState)
}// 享元工厂
type FlyweightFactory struct {flyweights map[string]Flyweight
}func NewFlyweightFactory() *FlyweightFactory {return &FlyweightFactory{flyweights: make(map[string]Flyweight),}
}func (f *FlyweightFactory) GetFlyweight(key string) Flyweight {if flyweight, ok := f.flyweights[key]; ok {return flyweight}flyweight := &ConcreteFlyweight{intrinsicState: key}f.flyweights[key] = flyweightreturn flyweight
}func main() {factory := NewFlyweightFactory()flyweight1 := factory.GetFlyweight("A")flyweight1.Operation("1")flyweight2 := factory.GetFlyweight("A")flyweight2.Operation("2")flyweight3 := factory.GetFlyweight("B")flyweight3.Operation("3")
}
Mermaid图
«interface»
Flyweight
+Operation(string)
ConcreteFlyweight
+string intrinsicState
+Operation(string)
FlyweightFactory
+map[string, Flyweight> flyweights
+GetFlyweight(string) : Flyweight
12. 代理模式 (Proxy)

代理模式为其他对象提供一种代理以控制对这个对象的访问。

Go代码示例
package mainimport "fmt"// 接口
type Subject interface {Request()
}// 真实主题
type RealSubject struct{}func (r *RealSubject) Request() {fmt.Println("真实主题请求")
}// 代理
type Proxy struct {realSubject *RealSubject
}func (p *Proxy) Request() {if p.realSubject == nil {p.realSubject = &RealSubject{}}fmt.Println("代理请求")p.realSubject.Request()
}func main() {proxy := &Proxy{}proxy.Request()
}
Mermaid图
«interface»
Subject
+Request()
RealSubject
+Request()
Proxy
-RealSubject realSubject
+Request()

行为型模式(11种)

13. 责任链模式 (Chain of Responsibility)

责任链模式通过给多个对象处理同一个请求来避免请求的发送者与接收者耦合。

Go代码示例
package mainimport "fmt"// 处理者接口
type Handler interface {SetNext(handler Handler)Handle(request int)
}// 基础处理者
type BaseHandler struct {next Handler
}func (h *BaseHandler) SetNext(handler Handler) {h.next = handler
}func (h *BaseHandler) Handle(request int) {if h.next != nil {h.next.Handle(request)}
}// 具体处理者1
type ConcreteHandler1 struct {BaseHandler
}func (h *ConcreteHandler1) Handle(requestint) {if request < 10 {fmt.Println("ConcreteHandler1 处理请求", request)} else {h.BaseHandler.Handle(request)}
}// 具体处理者2
type ConcreteHandler2 struct {BaseHandler
}func (h *ConcreteHandler2) Handle(request int) {if request >= 10 && request < 20 {fmt.Println("ConcreteHandler2 处理请求", request)} else {h.BaseHandler.Handle(request)}
}func main() {handler1 := &ConcreteHandler1{}handler2 := &ConcreteHandler2{}handler1.SetNext(handler2)requests := []int{5, 14, 22}for _, request := range requests {handler1.Handle(request)}
}
Mermaid图
«interface»
Handler
+SetNext(handler Handler)
+Handle(request int)
BaseHandler
+Handler next
+SetNext(handler Handler)
+Handle(request int)
ConcreteHandler1
+Handle(request int)
ConcreteHandler2
+Handle(request int)
14. 命令模式 (Command)

命令模式将请求封装为一个对象,从而使您可以用不同的请求对客户进行参数化,对请求排队或记录请求日志,以及支持可撤销的操作。

Go代码示例
package mainimport "fmt"// 命令接口
type Command interface {Execute()
}// 具体命令
type ConcreteCommand struct {receiver *Receiver
}func (c *ConcreteCommand) Execute() {c.receiver.Action()
}// 接收者
type Receiver struct{}func (r *Receiver) Action() {fmt.Println("接收者的动作")
}// 调用者
type Invoker struct {command Command
}func (i *Invoker) SetCommand(command Command) {i.command = command
}func (i *Invoker) Invoke() {i.command.Execute()
}func main() {receiver := &Receiver{}command := &ConcreteCommand{receiver: receiver}invoker := &Invoker{}invoker.SetCommand(command)invoker.Invoke()
}
Mermaid图
«interface»
Command
+Execute()
ConcreteCommand
+Receiver receiver
+Execute()
Receiver
+Action()
Invoker
+Command command
+SetCommand(command Command)
+Invoke()
15. 解释器模式 (Interpreter)

解释器模式定义了一个语言的文法,并且通过解释器来解释语言中的句子。

Go代码示例
package mainimport ("fmt""strings"
)// 表达式接口
type Expression interface {Interpret(context string) bool
}// 终端表达式
type TerminalExpression struct {data string
}func (t *TerminalExpression) Interpret(context string) bool {return strings.Contains(context, t.data)
}// 或表达式
type OrExpression struct {expr1, expr2 Expression
}func (o *OrExpression) Interpret(context string) bool {return o.expr1.Interpret(context) || o.expr2.Interpret(context)
}// 与表达式
type AndExpression struct {expr1, expr2 Expression
}func (a *AndExpression) Interpret(context string) bool {return a.expr1.Interpret(context) && a.expr2.Interpret(context)
}func main() {expr1 := &TerminalExpression{data: "Hello"}expr2 := &TerminalExpression{data: "World"}orExpr := &OrExpression{expr1: expr1, expr2: expr2}andExpr := &AndExpression{expr1: expr1, expr2: expr2}context1 := "Hello"context2 := "Hello World"fmt.Println("Context1 is 'Hello':", orExpr.Interpret(context1))fmt.Println("Context2 is 'Hello World':", andExpr.Interpret(context2))
}
Mermaid图
«interface»
Expression
+Interpret(context string) : bool
TerminalExpression
+string data
+Interpret(context string) : bool
OrExpression
+Expression expr1
+Expression expr2
+Interpret(context string) : bool
AndExpression
+Expression expr1
+Expression expr2
+Interpret(context string) : bool
16. 迭代器模式 (Iterator)

迭代器模式提供了一种方法,可以顺序访问集合对象中的元素,而不暴露集合对象的内部表示。这个模式主要用于提供一种遍历访问集合中的元素的方法。

Go语言代码示例
package mainimport "fmt"// Iterator 是迭代器接口,定义了遍历元素的相关方法
type Iterator interface {HasNext() boolNext() interface{}
}// Aggregate 是集合接口,定义了创建迭代器的方法
type Aggregate interface {CreateIterator() Iterator
}// ConcreteIterator 是具体的迭代器,实现了 Iterator 接口
type ConcreteIterator struct {collection *ConcreteAggregateindex      int
}func (i *ConcreteIterator) HasNext() bool {return i.index < len(i.collection.items)
}func (i *ConcreteIterator) Next() interface{} {item := i.collection.items[i.index]i.index++return item
}// ConcreteAggregate 是具体的集合,提供迭代器的实现
type ConcreteAggregate struct {items []interface{}
}func (a *ConcreteAggregate) CreateIterator() Iterator {return &ConcreteIterator{collection: a,index:      0,}
}func main() {aggregate := &ConcreteAggregate{items: []interface{}{"Item1", "Item2", "Item3"},}iterator := aggregate.CreateIterator()for iterator.HasNext() {item := iterator.Next()fmt.Println(item)}
}
Mermaid图示
"Creates"
«interface»
Iterator
+HasNext()
+Next()
«interface»
Aggregate
+CreateIterator()
ConcreteIterator
-collection: ConcreteAggregate
-index: int
+HasNext()
+Next()
ConcreteAggregate
-items: list
+CreateIterator()
17. 中介者模式 (Mediator)

中介者模式定义一个对象来封装一系列对象之间的交互,使得这些对象不需要显式地相互引用,从而使得它们可以松散耦合。

Go代码示例
package mainimport "fmt"// 中介者接口
type Mediator interface {Send(message string, colleague Colleague)
}// 同事接口
type Colleague interface {Send(message string)Receive(message string)
}// 具体同事1
type ConcreteColleague1 struct {mediator Mediator
}func (c *ConcreteColleague1) Send(message string) {c.mediator.Send(message, c)
}func (c *ConcreteColleague1) Receive(message string) {fmt.Println("ConcreteColleague1 收到消息:", message)
}// 具体同事2
type ConcreteColleague2 struct {mediator Mediator
}func (c *ConcreteColleague2) Send(message string) {c.mediator.Send(message, c)
}func (c *ConcreteColleague2) Receive(message string) {fmt.Println("ConcreteColleague2 收到消息:", message)
}// 具体中介者
type ConcreteMediator struct {colleague1 *ConcreteColleague1colleague2 *ConcreteColleague2
}func (m *ConcreteMediator) Send(message string, colleague Colleague) {if colleague == m.colleague1 {m.colleague2.Receive(message)} else {m.colleague1.Receive(message)}
}func main() {mediator := &ConcreteMediator{}colleague1 := &ConcreteColleague1{mediator: mediator}colleague2 := &ConcreteColleague2{mediator: mediator}mediator.colleague1 = colleague1mediator.colleague2 = colleague2colleague1.Send("Hello from Colleague1")colleague2.Send("Hello from Colleague2")
}
Mermaid图
«interface»
Mediator
+Send(message string, colleague Colleague)
«interface»
Colleague
+Send(message string)
+Receive(message string)
ConcreteColleague1
+Mediator mediator
+Send(message string)
+Receive(message string)
ConcreteColleague2
+Mediator mediator
+Send(message string)
+Receive(message string)
ConcreteMediator
+ConcreteColleague1 colleague1
+ConcreteColleague2 colleague2
+Send(message string, colleague Colleague)
18. 状态模式 (State)

状态模式允许对象在内部状态改变时改变其行为,对象看起来好像修改了它的类一样。

Go代码示例
package mainimport "fmt"// 状态接口
type State interface {Handle(context *Context)
}// 具体状态A
type ConcreteStateA struct{}func (s *ConcreteStateA) Handle(context *Context) {fmt.Println("状态A处理请求")context.SetState(&ConcreteStateB{})
}// 具体状态B
type ConcreteStateB struct{}func (s *ConcreteStateB) Handle(context *Context) {fmt.Println("状态B处理请求")context.SetState(&ConcreteStateA{})
}// 上下文
type Context struct {state State
}func (c *Context) SetState(state State) {c.state = state
}func (c *Context) Request() {c.state.Handle(c)
}func main() {context := &Context{state: &ConcreteStateA{}}context.Request()context.Request()context.Request()
}
Mermaid图
«interface»
State
+Handle(context *Context)
ConcreteStateA
+Handle(context *Context)
ConcreteStateB
+Handle(context *Context)
Context
-State state
+SetState(state State)
+Request()
19. 策略模式 (Strategy)

策略模式定义一系列算法,把它们一个个封装起来,并且使它们可以互换。策略模式让算法的变化独立于使用算法的客户。

Go代码示例
package mainimport "fmt"// 策略接口
type Strategy interface {Execute(a, b int) int
}// 具体策略A
type ConcreteStrategyAdd struct{}func (s *ConcreteStrategyAdd) Execute(a, b int) int {return a + b
}// 具体策略B
type ConcreteStrategySubtract struct{}func (s *ConcreteStrategySubtract) Execute(a, b int) int {return a - b
}// 上下文
type Context struct {strategy Strategy
}func (c *Context) SetStrategy(strategy Strategy) {c.strategy = strategy
}func (c *Context) ExecuteStrategy(a, b int) int {return c.strategy.Execute(a, b)
}func main() {context := &Context{}context.SetStrategy(&ConcreteStrategyAdd{})fmt.Println("加法:", context.ExecuteStrategy(3, 4))context.SetStrategy(&ConcreteStrategySubtract{})fmt.Println("减法:", context.ExecuteStrategy(7, 5))
}
Mermaid图
«interface»
Strategy
+Execute(a int, b int) : int
ConcreteStrategyAdd
+Execute(a int, b int) : int
ConcreteStrategySubtract
+Execute(a int, b int) : int
Context
-Strategy strategy
+SetStrategy(strategy Strategy)
+ExecuteStrategy(a int, b int) : int
20. 模板方法模式 (Template Method)

模板方法模式定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以不改变一个算法的结构即可重新定义该算法的某些特定步骤。

Go代码示例
package mainimport "fmt"// 抽象类
type AbstractClass interface {TemplateMethod()PrimitiveOperation1()PrimitiveOperation2()
}// 具体类
type ConcreteClass struct{}func (c *ConcreteClass) TemplateMethod() {c.PrimitiveOperation1()c.PrimitiveOperation2()
}// 抽象步骤1
func (c *ConcreteClass) PrimitiveOperation1() {fmt.Println("ConcreteClass PrimitiveOperation1")
}// 抽象步骤2
func (c *ConcreteClass) PrimitiveOperation2() {fmt.Println("ConcreteClass PrimitiveOperation2")
}func main() {concreteClass := &ConcreteClass{}concreteClass.TemplateMethod()
}
Mermaid图
«interface»
AbstractClass
+TemplateMethod()
+PrimitiveOperation1()
+PrimitiveOperation2()
ConcreteClass
+TemplateMethod()
+PrimitiveOperation1()
+PrimitiveOperation2()
21. 访问者模式 (Visitor)

访问者模式表示一个作用于某对象结构中的各元素的操作,它使你可以在不改变这些元素的类的前提下定义作用于这些元素的新操作。

Go代码示例
package mainimport "fmt"// 访问者接口
type Visitor interface {VisitElementA(elementA *ElementA)VisitElementB(elementB *ElementB)
}// 具体访问者
type ConcreteVisitor struct{}func (v *ConcreteVisitor) VisitElementA(elementA *ElementA) {fmt.Println("访问者访问ElementA")
}func (v *ConcreteVisitor) VisitElementB(elementB *ElementB) {fmt.Println("访问者访问ElementB")
}// 元素接口
type Element interface {Accept(visitor Visitor)
}// 具体元素A
type ElementA struct{}func (e *ElementA) Accept(visitor Visitor) {visitor.VisitElementA(e)
}// 具体元素B
type ElementB struct{}func (e *ElementB) Accept(visitor Visitor) {visitor.VisitElementB(e)
}func main() {visitor := &ConcreteVisitor{}elementA := &ElementA{}elementB := &ElementB{}elementA.Accept(visitor)elementB.Accept(visitor)
}
Mermaid图
«interface»
Visitor
+VisitElementA(elementA *ElementA)
+VisitElementB(elementB *ElementB)
ConcreteVisitor
+VisitElementA(elementA *ElementA)
+VisitElementB(elementB *ElementB)
«interface»
Element
+Accept(visitor Visitor)
ElementA
+Accept(visitor Visitor)
ElementB
+Accept(visitor Visitor)

确实,之前展示了21种设计模式。以下是剩余的2种设计模式(代理模式和备忘录模式)的Go语言实现和Mermaid图表示。

22. 代理模式 (Proxy)

代理模式提供了一个代理对象,控制对其他对象的访问,允许在访问目标对象之前或之后执行一些处理。

Go代码示例
package mainimport "fmt"// 抽象主题
type Subject interface {Request()
}// 真实主题
type RealSubject struct{}func (r *RealSubject) Request() {fmt.Println("RealSubject: Handling request")
}// 代理
type Proxy struct {realSubject *RealSubject
}func (p *Proxy) Request() {if p.realSubject == nil {p.realSubject = &RealSubject{}}fmt.Println("Proxy: Checking access before real subject")p.realSubject.Request()fmt.Println("Proxy: Logging request after real subject")
}func main() {proxy := &Proxy{}proxy.Request()
}
Mermaid图
«interface»
Subject
+Request()
RealSubject
+Request()
Proxy
-RealSubject realSubject
+Request()
23. 备忘录模式 (Memento)

备忘录模式在不暴露对象内部结构的情况下,捕获对象的内部状态,以便在以后恢复对象的状态。

Go代码示例
package mainimport "fmt"// 发起人
type Originator struct {state string
}func (o *Originator) SetState(state string) {o.state = statefmt.Println("Originator: Setting state to", state)
}func (o *Originator) SaveStateToMemento() *Memento {return &Memento{state: o.state}
}func (o *Originator) RestoreStateFromMemento(memento *Memento) {o.state = memento.statefmt.Println("Originator: State restored from Memento to", o.state)
}// 备忘录
type Memento struct {state string
}// 负责人
type Caretaker struct {memento *Memento
}func (c *Caretaker) Save(memento *Memento) {c.memento = memento
}func (c *Caretaker) Restore() *Memento {return c.memento
}func main() {originator := &Originator{}caretaker := &Caretaker{}originator.SetState("State1")caretaker.Save(originator.SaveStateToMemento())originator.SetState("State2")fmt.Println("Current State:", originator.state)originator.RestoreStateFromMemento(caretaker.Restore())fmt.Println("Restored State:", originator.state)
}
Mermaid图
Originator
-string state
+SetState(state string)
+SaveStateToMemento() : Memento
+RestoreStateFromMemento(memento Memento)
Memento
-string state
Caretaker
-Memento memento
+Save(memento Memento)
+Restore() : Memento

以上代码和Mermaid图展示了设计模式的完整实现,希望这些示例能帮助你更好地理解和运用这些设计模式。

完。
在这里插入图片描述
希望对您有所帮助!关注锅总,及时获得更多花里胡哨的运维实用操作!

三、一个秘密

图片

锅总个人博客

https://gentlewok.blog.csdn.net/

锅总微信公众号

图片

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/43696.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Apache AGE 安装部署

AGE概述 概述 我们可以通过源码安装、拉取docker镜像运行、直接使用公有云三种方式中的任意一种来使用Apache AGE 获取 AGE 发布版本 可以在 https://github.com/apache/age/releases 找到发布版本和发布说明。 源代码 源代码可以在 https://github.com/apache/age 找到…

PowerShell install 一键部署mysql 9.0.0

mysql 前言 MySQL 是一个基于 SQL(Structured Query Language)的数据库系统,SQL 是一种用于访问和管理数据库的标准语言。MySQL 以其高性能、稳定性和易用性而闻名,它被广泛应用于各种场景,包括: Web 应用程序:许多动态网站和内容管理系统(如 WordPress)使用 MySQL 存…

【割点 C++BFS】2556. 二进制矩阵中翻转最多一次使路径不连通

本文涉及知识点 割点 图论知识汇总 CBFS算法 LeetCode2556. 二进制矩阵中翻转最多一次使路径不连通 给你一个下标从 0 开始的 m x n 二进制 矩阵 grid 。你可以从一个格子 (row, col) 移动到格子 (row 1, col) 或者 (row, col 1) &#xff0c;前提是前往的格子值为 1 。如…

AE常用工具

目录 图形工具&#xff08;快捷键Q&#xff09; 选取工具&#xff08;快捷键V&#xff09; 抓手工具&#xff08;快捷键H或空格&#xff09; 放缩工具&#xff08;快捷键Z或滚动滑轮&#xff09; 图形工具&#xff08;快捷键Q&#xff09; 按住alt并点击&#xff0c;可切换…

单目深度估计部署 rk3588

搞了一小段时间的单目深度估计&#xff0c;目标是在板端部署用起来&#xff0c;但由于基于开源数据或开源模型&#xff0c;将模型估计的相对深度转换成绝对深度误差非常大&#xff08;或许是转换方法有问题&#xff09;&#xff0c;另一方面如何具体的在项目中用起来还没好的想…

二重积分 - 包括计算方法和可视化

二重积分 - 包括计算方法和可视化 flyfish 计算在矩形区域 R [ 0 , 1 ] [ 0 , 2 ] R [0, 1] \times [0, 2] R[0,1][0,2] 下&#xff0c;函数 z 8 x 6 y z 8x 6y z8x6y 的二重积分。这相当于计算曲面 z 8 x 6 y z 8x 6y z8x6y 与 xy 平面之间的体积。 二重积分…

UMI HTTP接口手册

Translate to English 命令行手册&#xff1a; README_CLI.mdHTTP接口手册&#xff1a; README_HTTP.md HTTP接口手册 &#xff08;本文档仅适用于 Umi-OCR 最新版本。旧版本请查看 Github备份分支 中对应版本的文档。&#xff09; 基础说明 如上图&#xff0c;必须允许HTT…

Java内存区域与内存溢出异常(补充)

2.2.5 方法区 方法区(Method Area)与Java堆一样&#xff0c;是各个线程共享的内存区域&#xff0c;它用于存储已被虚拟机加载的类型信息、常量、静态变量、即时编译器编译后的代码缓存等数据。虽然《Java虚拟机规范》中把方法区描述为堆的一个逻辑部分&#xff0c;但是它却有一…

2024浙江外国语学院汉语桥线上项目 “在杭州,看见更好的中国”开班

7月9日上午&#xff0c;由教育部中外语言交流合作中心主办、浙江外国语学院国际商学院承办的2024汉语桥“在杭州&#xff0c;看见更好的中国”线上项目正式启动。项目负责人何骅老师及汉语桥教师团队&#xff0c;与来自越南、缅甸、日本、俄罗斯的100名学员相聚云端&#xff0c…

Nginx配置基础

ect/nginx/nginx.conf配置 1&#xff09;nginx 相关目录 工作目录&#xff1a;ect/nginx 家目录 执行文件&#xff1a;/usr/sbin/nginx 启动或重载 sudo /usr/sbin/nginx -t 检查配置文件 sudo /usr/sbin/nginx -s reload 重启服务 日志文件&#xff1a;/var/log/nginx 启动文…

计算机视觉研究方向初学习,计算机视觉都有什么方向??!到底是干什么的?!

计算机视觉研究方向初学习&#xff0c;计算机视觉都有什么方向&#xff1f;&#xff1f;&#xff01;到底是干什么的&#xff1f;&#xff01; 语义分割图像分类目标检测和定位实例分割、全景分割物体跟踪姿态估计人脸识别人体识别图像增强风格迁移图像生成视觉问答视频分析光学…

SpringBoot实战:轻松实现接口数据脱敏

文章目录 引言一、接口数据脱敏概述1.1 接口数据脱敏的定义1.2 接口数据脱敏的重要性1.3 接口数据脱敏的实现方式 二、开发环境三、实现接口返回数据脱敏3.1 添加依赖3.2 创建自定义注解3.3 定义脱敏枚举类3.4 创建自定义序列化类 四、测试4.1 编写测试代码4.2 测试 五、总结 引…

C++基础(七):类和对象(中-2)

上一篇博客学的默认成员函数是类和对象的最重要的内容&#xff0c;相信大家已经掌握了吧&#xff0c;这一篇博客接着继续剩下的内容&#xff0c;加油&#xff01; 目录 一、const成员&#xff08;理解&#xff09; 1.0 引入 1.1 概念 1.2 总结 1.2.1 对象调用成员函数 …

自动群发消息插件常用源代码科普!

随着网络技术的快速发展&#xff0c;自动群发消息插件成为了众多企业和个人提高效率、加强沟通的重要工具。 然而&#xff0c;开发一个高效且稳定的自动群发消息插件并非易事&#xff0c;需要深入理解并熟练掌握相关的源代码。 本文将从五个方面&#xff0c;通过具体的源代码…

通俗易懂--.csproj 文件

.csproj 文件 .csproj&#xff0c;是C#项目文件的扩展名&#xff0c;它是“C Sharp Project”的缩写。.net开发环境中建立项目时&#xff0c;会产生.csproj文件&#xff0c;这是C#的工程文件&#xff0c;其中记录了与工程有关的相关信息&#xff0c;例如包含的文件&#xff0c;…

2024第六届上海国际新材料展览会-12月精彩呈现

2024第六届上海国际新材料展览会 The 6th shanghai International New Materials Exhibition in 2024 时 间&#xff1a;2024年12月18-20日 地 点&#xff1a;上海新国际博览中心 CIME 2024专业、权威&#xff0c;涵盖整个新材料行业的国际盛会。 期待与您在CIME 2024现场相…

【INTEL(ALTERA)】为什么我使用 PIO 边缘捕获中断的 Nios® II 设计不能正常工作?

目录 说明 解决方法 说明 当用户选择了不正确的边缘捕获设置&#xff0c;从而阻止触发中断时&#xff0c;可能会出现此问题。 在 PIO&#xff08;并行 I/O&#xff09;英特尔 FPGA IP内核中&#xff0c;如果“启用单个位设置/清除”选项被关闭&#xff0c;则将任何值写入边…

【购物车案例】for循环为什么使用key

要做出一个简单的购物车界面。首先&#xff0c;有一个复选框&#xff0c;可以选择商品&#xff0c;后面紧跟的是商品名称&#xff0c;然后&#xff0c;是删除按钮&#xff0c;根据这个需求&#xff0c;先写出一个简单的界面&#xff0c;代码如下&#xff1a; <template>…

openssh9.8p1更新 修复漏洞(CVE-2024-6387)

2024 年 7 月&#xff0c;互联网公开披露了一个 OpenSSH 的远程代码执行漏洞&#xff08;CVE-2024-6387&#xff09;。鉴于该漏洞虽然利用较为困难但危害较大&#xff0c;建议所有使用受影响的企业尽快修复该漏洞。 centos7 为例 yum -y install gcc make openssl-devel zlib…

三相感应电机的建模仿真(3)基于ABC相坐标系Level2 S-Fun以及定子串不对称电抗起动过程仿真分析

1. 概述 2. 三相感应电动机状态方程式 3. 基于Level2 S-Function的仿真模型建立 4. 动态分析实例 5. 总结 6. 参考文献 1. 概述 三相感应电机自然坐标系下的数学模型是一组周期性变系数微分方程(其电感矩阵是转子位置角的函数,转子位置角随时间按正弦规律变化),将其用…