通过复制、拷贝或者叫克隆已有对象的方式来创建新对象的设计模式叫做原型模式,被拷贝的对象也被称作原型对象。
项目的准备工作
1.找到 go 的 GOPATH
$ go env //可以查看 GOPATH
2.在 GOPATH 目录下创建3个文件夹
1.bin文件夹 -- 存放编译后的二进制文件
2.pkg文件夹 -- 存放编译后的库文件
3.src文件夹 -- 存放源码文件
3.解决运行错误
GO111MODULE="" //如果是这样,运行会报错
错误: package design/factory_met/module/factory is not in GOROOT
GO111MODULE=off 无模块支持,go 会从 GOPATH 和 vendor 文件夹寻找包。
GO111MODULE=on 模块支持,go 会忽略 GOPATH 和 vendor 文件夹,只根据 go.mod 下载依赖。
GO111MODULE=auto 在 $GOPATH/src 外面且根目录有 go.mod 文件时,开启模块支持。
// 将GO111MODULE修改为off,在终端输入go env -w GO111MODULE=off
4.为项目创建文件夹
// 在项目文件夹 prototype_case 里创建新文件夹
// prototype -- 存放原型的全部文件
原型模式的实现代码
1.接口文件 -- prototype文件夹
文件1 -- shapeclone.go
package prototype
//ShapeClone 有克隆方法的接口
type ShapeClone interface {
Clone() ShapeClone
}
2.结构体文件 -- prototype文件夹
1.原型管理类
文件1 -- shapemanager.go
package prototype
//ShapeManager 模型管理类,用于保存所有Clone接口的原型
type ShapeManager struct {
ShapeList map[string]ShapeClone
}
//NewShapeManager 新建模型管理类
func NewShapeManager() *ShapeManager {
return &ShapeManager{
ShapeList: make(map[string]ShapeClone),
}
}
//Set 添加原型
func (s *ShapeManager) Set(name string, proto ShapeClone) {
s.ShapeList[name] = proto
}
//Get 获取原型
func (s *ShapeManager) Get(name string) ShapeClone {
return s.ShapeList[name]
}
2.原型类
文件1 -- circle.go
package prototype
//Circle 圆形类,实现shapeclone接口
type Circle struct {
Name string
}
//NewCircle 新建一个CIrcle类
func NewCircle(name string) *Circle {
return &Circle{Name: name}
}
//GetName 获取circle的名字
func (c *Circle) GetName() string {
return c.Name
}
//Clone 返回circle类的复制
func (c *Circle) Clone() ShapeClone {
circleClone := c
return circleClone
}
//Draw circle的方法
func (c *Circle) Draw() {
fmt.Println("Circle Draw().")
}
3.主文件 -- main.go 在项目文件夹
package main
import (
"design/prototype_case/prototype"
"fmt"
)
// 具体工作
func main() {
//1-创建一个原型管理者
sManager := prototype.NewShapeManager()
fmt.Printf("原型管理者: %s\n", sManager)
//2-创建一个圆形
circle_1 := prototype.NewCircle("圆形-1号")
fmt.Printf("圆形1: %s\n", circle_1)
//3-创建一个圆形克隆对象
circle_clone := circle_1.Clone()
fmt.Printf("圆形1克隆:%s\n", circle_clone)
//4-给原型管理者增加 map 参数
sManager.Set("circle_1",circle_1)
fmt.Printf("原型管理者: %s\n", sManager)
fmt.Printf("原型管理者的circle_1:%v\n\n", sManager.Get("circle_1"))
//5-改变原型数据,克隆数据、原型管理者的 map 也跟着改变
circle_1.Name = "园子"
fmt.Printf("圆形1: %s\n", circle_1)
fmt.Printf("圆形1克隆:%s\n", circle_clone)
fmt.Printf("原型管理者的circle_1:%v\n", sManager.Get("circle_1"))
}