From 357c4748f8a08d17079209bd3317626d0c7d6a60 Mon Sep 17 00:00:00 2001 From: IvisTang Date: Thu, 11 Dec 2025 16:57:10 +0800 Subject: [PATCH] =?UTF-8?q?=E6=9B=B4=E6=96=B0=E5=90=84=E4=B8=AA=E8=AE=BE?= =?UTF-8?q?=E8=AE=A1=E6=A8=A1=E5=BC=8F=E7=A4=BA=E4=BE=8B=EF=BC=8C=E6=B7=BB?= =?UTF-8?q?=E5=8A=A0=E5=B7=A5=E5=8E=82=E6=96=B9=E6=B3=95=E3=80=81=E5=8E=9F?= =?UTF-8?q?=E5=9E=8B=E5=92=8C=E5=8D=95=E4=BE=8B=E6=A8=A1=E5=BC=8F=E7=9A=84?= =?UTF-8?q?=E5=AE=9E=E7=8E=B0=EF=BC=8C=E9=87=8D=E6=9E=84=E7=9B=B8=E5=85=B3?= =?UTF-8?q?=E4=BB=A3=E7=A0=81=E5=B9=B6=E5=A2=9E=E5=BC=BA=E5=8F=AF=E8=AF=BB?= =?UTF-8?q?=E6=80=A7?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- go/factory_method/main.go | 68 +++++++++++++++++++++++++++ go/prototype/main.go | 81 ++++++++++++++++++++++++++++++++ go/singleton/main.go | 44 ++++++++++++++++++ python/factory_method/main.py | 64 ++++++++++++++++++++++++++ python/prototype/main.py | 84 ++++++++++++++++++++++++++++++++++ python/singleton/main.py | 42 +++++++++++++++++ ts/src/builder/index.ts | 2 +- ts/src/factory_method/index.ts | 59 ++++++++++++++++++++++++ ts/src/prototype/index.ts | 81 ++++++++++++++++++++++++++++++++ ts/src/singleton/index.ts | 34 ++++++++++++++ 10 files changed, 558 insertions(+), 1 deletion(-) create mode 100644 go/factory_method/main.go create mode 100644 go/prototype/main.go create mode 100644 go/singleton/main.go create mode 100644 python/factory_method/main.py create mode 100644 python/prototype/main.py create mode 100644 python/singleton/main.py create mode 100644 ts/src/factory_method/index.ts create mode 100644 ts/src/prototype/index.ts create mode 100644 ts/src/singleton/index.ts diff --git a/go/factory_method/main.go b/go/factory_method/main.go new file mode 100644 index 0000000..7771d90 --- /dev/null +++ b/go/factory_method/main.go @@ -0,0 +1,68 @@ +package main + +/* +实例 +小汤有一家披萨店,他想通过工厂方法模式来创建不同类型的披萨。 +首先,他定义了一个披萨接口和具体的披萨类,然后创建了一个披萨工厂接口和具体的披萨工厂类来生产不同类型的披萨。 +*/ + +import "fmt" + +// 披萨接口 +type Pizza interface { + show() +} + +// 披萨工厂接口 +type PizzaFactory interface { + createPizza() Pizza +} + +// 具体的披萨类 +type CheesePizza struct{} + +func (p *CheesePizza) show() { + fmt.Println(" 这是个芝士披萨!") + fmt.Println() +} + +type PepperoniPizza struct{} + +func (p *PepperoniPizza) show() { + fmt.Println(" 这是个意大利辣香肠披萨!") + fmt.Println() +} + +// 具体的披萨工厂类 +type CheesePizzaFactory struct{} + +func (f *CheesePizzaFactory) createPizza() Pizza { + return &CheesePizza{} +} + +type PepperoniPizzaFactory struct{} + +func (f *PepperoniPizzaFactory) createPizza() Pizza { + return &PepperoniPizza{} +} + +func main() { + var factory PizzaFactory + var pizza Pizza + + fmt.Println("========= 工厂方法模式 =========") + + // 创建芝士披萨 + factory = &CheesePizzaFactory{} + fmt.Println("芝士披萨工厂启动:") + pizza = factory.createPizza() + pizza.show() + + // 创建意大利辣香肠披萨 + factory = &PepperoniPizzaFactory{} + fmt.Println("意大利辣香肠披萨工厂启动:") + pizza = factory.createPizza() + pizza.show() + + fmt.Println("======= 工厂方法模式结束 =======") +} diff --git a/go/prototype/main.go b/go/prototype/main.go new file mode 100644 index 0000000..0e16bbe --- /dev/null +++ b/go/prototype/main.go @@ -0,0 +1,81 @@ +package main + +/* +实例 +汤宝宝穿越到了星球大战世界,并掉到了克隆人军队的生产工厂。 + +ps: +go中没有官方的深拷贝实现,一些第三方库会使用reflect的方式来实现深拷贝,但性能较差且不够类型安全。 +比较安全的方法是逐步复制每个字段,会有稍许麻烦。 +*/ + +import "fmt" + +// 克隆人接口 +type CloneTrooper interface { + clone() CloneTrooper + fight() + setid(id int) +} + +// 具体的克隆人类 +type CloneTrooperA struct { + Id int +} + +func (c *CloneTrooperA) clone() CloneTrooper { + fmt.Printf("克隆人A-%d号正在克隆...\n", c.Id) + return &CloneTrooperA{Id: c.Id} +} + +func (c *CloneTrooperA) fight() { + fmt.Printf("克隆人A-%d号准备战斗!\n", c.Id) +} + +func (c *CloneTrooperA) setid(id int) { + c.Id = id +} + +type CloneTrooperB struct { + Id int +} + +func (c *CloneTrooperB) clone() CloneTrooper { + fmt.Printf("克隆人B-%d号正在克隆...\n", c.Id) + return &CloneTrooperB{Id: c.Id} +} + +func (c *CloneTrooperB) fight() { + fmt.Printf("克隆人B-%d号准备战斗!\n", c.Id) +} + +func (c *CloneTrooperB) setid(id int) { + c.Id = id +} + +func main() { + fmt.Println("========= 原型模式 =========") + + // 创建克隆人A原型 + prototypeA := &CloneTrooperA{Id: 0} + prototypeA.fight() + cloneA1 := prototypeA.clone() + cloneA1.setid(1) + cloneA1.fight() + cloneA2 := cloneA1.clone() + cloneA2.setid(2) + cloneA2.fight() + + // 创建克隆人B原型 + prototypeB := &CloneTrooperB{Id: 0} + prototypeB.fight() + cloneB1 := prototypeB.clone() + cloneB1.setid(1) + cloneB1.fight() + cloneB2 := cloneB1.clone() + cloneB2.setid(2) + cloneB2.fight() + + fmt.Println() + fmt.Println("======= 原型模式结束 =======") +} diff --git a/go/singleton/main.go b/go/singleton/main.go new file mode 100644 index 0000000..b36a6dd --- /dev/null +++ b/go/singleton/main.go @@ -0,0 +1,44 @@ +package main + +/* +实例 +汤宝宝混穿到了泰拉世界,并成为了泰拉联邦的唯一统治者。人类只有一个帝皇! +*/ + +import ( + "fmt" + "sync" +) + +// 帝皇类 +type Emperor struct { + Name string +} + +var emperorInstance *Emperor +var once sync.Once + +// 获取帝皇实例的函数 +func GetEmperorInstance(name string, announce string) *Emperor { + fmt.Println(announce) + once.Do(func() { + emperorInstance = &Emperor{Name: name} + }) + return emperorInstance +} + +func main() { + + fmt.Println("========= 单例模式 =========") + + // 获取帝皇实例 + emperor1 := GetEmperorInstance("汤宝宝", "泰拉联邦的帝皇诞生了!") + fmt.Printf("帝皇的名字是:%s!\n", emperor1.Name) + emperor2 := GetEmperorInstance("王二狗", "泰拉联邦的帝皇又一次诞生了!") + fmt.Printf("帝皇的名字是:%s!\n", emperor2.Name) + if emperor1 == emperor2 { + fmt.Printf("泰拉只有一个帝皇:%s!\n\n", emperor1.Name) + } + + fmt.Println("======= 单例模式结束 =======") +} diff --git a/python/factory_method/main.py b/python/factory_method/main.py new file mode 100644 index 0000000..7c31298 --- /dev/null +++ b/python/factory_method/main.py @@ -0,0 +1,64 @@ +""" +实例 +小汤有一家披萨店,他想通过工厂方法模式来创建不同类型的披萨。 +首先,他定义了一个披萨接口和具体的披萨类,然后创建了一个披萨工厂接口和具体的披萨工厂类来生产不同类型的披萨。 +""" + +from abc import ABC, abstractmethod + + +# 披萨接口 +class Pizza(ABC): + @abstractmethod + def show(self): + pass + + +# 披萨工厂接口 +class PizzaFactory(ABC): + @abstractmethod + def createPizza(self) -> Pizza: + pass + + +# 具体的披萨类 +class CheesePizza(Pizza): + def show(self): + print(" 这是个芝士披萨!\n") + + +class PepperoniPizza(Pizza): + def show(self): + print(" 这是个意大利辣香肠披萨!\n") + + +# 具体的披萨工厂类 +class CheesePizzaFactory(PizzaFactory): + def createPizza(self) -> Pizza: + return CheesePizza() + + +class PepperoniPizzaFactory(PizzaFactory): + def createPizza(self) -> Pizza: + return PepperoniPizza() + + +def main(): + print("========= 工厂方法模式 =========") + # 创建芝士披萨 + factory = CheesePizzaFactory() + print("芝士披萨工厂启动:") + pizza = factory.createPizza() + pizza.show() + + # 创建意大利辣香肠披萨 + factory = PepperoniPizzaFactory() + print("意大利辣香肠披萨工厂启动:") + pizza = factory.createPizza() + pizza.show() + + print("======= 工厂方法模式结束 =======") + + +if __name__ == "__main__": + main() diff --git a/python/prototype/main.py b/python/prototype/main.py new file mode 100644 index 0000000..8e9a5de --- /dev/null +++ b/python/prototype/main.py @@ -0,0 +1,84 @@ +""" +实例 +汤宝宝穿越到了星球大战世界,并掉到了克隆人军队的生产工厂。 +""" + +from abc import ABC, abstractmethod +from copy import deepcopy + + +# 克隆人接口 +class CloneTrooper(ABC): + @abstractmethod + def clone(self) -> "CloneTrooper": + pass + + @abstractmethod + def fight(self): + pass + + @abstractmethod + def setid(self, id: int): + pass + + +# 具体的克隆人类 +class CloneTrooperA(CloneTrooper): + def __init__(self, id: int): + self.id = id + + def clone(self): + print(f"克隆人A-{self.id}号正在克隆...") + return deepcopy(self) + + def fight(self): + print(f"克隆人A-{self.id}号准备战斗!") + + def setid(self, id: int): + self.id = id + + +class CloneTrooperB(CloneTrooper): + def __init__(self, id: int): + self.id = id + + def clone(self): + print(f"克隆人B-{self.id}号正在克隆...") + return deepcopy(self) + + def fight(self): + print(f"克隆人B-{self.id}号准备战斗!") + + def setid(self, id: int): + self.id = id + + +def main(): + print("========= 原型模式 =========") + # 创建原型克隆人A + prototype_a = CloneTrooperA(0) + prototype_a.fight() + clone_a1 = prototype_a.clone() + clone_a1.setid(1) + clone_a1.fight() + + clone_a2 = clone_a1.clone() + clone_a2.setid(2) + clone_a2.fight() + + # 创建原型克隆人B + prototype_b = CloneTrooperB(0) + prototype_b.fight() + clone_b1 = prototype_b.clone() + clone_b1.setid(1) + clone_b1.fight() + + clone_b2 = clone_b1.clone() + clone_b2.setid(2) + clone_b2.fight() + + print("\n======= 原型模式结束 =======") + + +if __name__ == "__main__": + main() diff --git a/python/singleton/main.py b/python/singleton/main.py new file mode 100644 index 0000000..a0f0882 --- /dev/null +++ b/python/singleton/main.py @@ -0,0 +1,42 @@ +""" +实例 +汤宝宝混穿到了泰拉世界,并成为了泰拉联邦的唯一统治者。人类只有一个帝皇! +""" + + +# 帝皇类 +class Emperor(object): + __instance = None + __name = "" + + def __new__(cls, name: str, announce: str): + if not cls.__instance: + cls.__instance = super(Emperor, cls).__new__(cls) + cls.__instance.__name = name + return cls.__instance + + def __init__(self, name: str, announce: str) -> None: + print(announce) + + @property + def name(self) -> str: + return self.__name + + +def main() -> None: + print("========= 单例模式 =========") + + # 创建帝皇 + emperor1 = Emperor("汤宝宝", "泰拉联邦的帝皇诞生了!") + print(f"帝皇的名字是:{emperor1.name}!") + emperor2 = Emperor("王二狗", "泰拉联邦的帝皇又一次诞生了!") + print(f"帝皇的名字是:{emperor2.name}!") + + if emperor1 is emperor2: + print(f"泰拉只有一个帝皇:{emperor1.name}!\n") + + print("======= 单例模式结束 =======") + + +if __name__ == "__main__": + main() diff --git a/ts/src/builder/index.ts b/ts/src/builder/index.ts index 55c0aaf..26622c4 100644 --- a/ts/src/builder/index.ts +++ b/ts/src/builder/index.ts @@ -97,7 +97,7 @@ class Director { } (function () { - console.log("======== 建造者模式 ========"); + console.log("======== 生成者模式 ========"); const director = new Director(); diff --git a/ts/src/factory_method/index.ts b/ts/src/factory_method/index.ts new file mode 100644 index 0000000..1e7dd96 --- /dev/null +++ b/ts/src/factory_method/index.ts @@ -0,0 +1,59 @@ +/* +实例 +小汤有一家披萨店,他想通过工厂方法模式来创建不同类型的披萨。 +首先,他定义了一个披萨接口和具体的披萨类,然后创建了一个披萨工厂接口和具体的披萨工厂类来生产不同类型的披萨。 +*/ + +// 披萨接口 +interface Pizza { + show(): void; +} + +// 披萨工厂接口 +interface PizzaFactory { + createPizza(): Pizza; +} + +// 具体的披萨类 +class CheesePizza implements Pizza { + show(): void { + console.log(" 这是个芝士披萨!\n"); + } +} + +class PepperoniPizza implements Pizza { + show(): void { + console.log(" 这是个意大利辣味披萨!\n"); + } +} + +// 具体的披萨工厂类 +class CheesePizzaFactory implements PizzaFactory { + createPizza(): Pizza { + return new CheesePizza(); + } +} + +class PepperoniPizzaFactory implements PizzaFactory { + createPizza(): Pizza { + return new PepperoniPizza(); + } +} + +(function () { + console.log("========= 工厂方法模式 ========="); + + // 创建芝士披萨 + let factory: PizzaFactory = new CheesePizzaFactory(); + console.log("芝士披萨工厂启动:"); + let pizza: Pizza = factory.createPizza(); + pizza.show(); + + // 创建意大利辣味披萨 + factory = new PepperoniPizzaFactory(); + console.log("意大利辣味披萨工厂启动:"); + pizza = factory.createPizza(); + pizza.show(); + + console.log("======= 工厂方法模式结束 ======="); +})(); diff --git a/ts/src/prototype/index.ts b/ts/src/prototype/index.ts new file mode 100644 index 0000000..76370e5 --- /dev/null +++ b/ts/src/prototype/index.ts @@ -0,0 +1,81 @@ +/* +实例 +汤宝宝穿越到了星球大战世界,并掉到了克隆人军队的生产工厂。 + +ps: +ts中没有官方的深拷贝实现,lodash中有deepclone函数以深拷贝对象,但性能较差。 +object.assign和扩展运算符只能实现浅拷贝,JSON.parse(JSON.stringify(obj))虽然能实现深拷贝,但会丢失函数、undefined、symbol等特殊值,且无法处理循环引用的对象。 +比较安全的方法是逐步复制每个字段,会有稍许麻烦。 +*/ + +// 克隆人接口 +interface CloneTrooper { + clone(): CloneTrooper; + fight(): void; + setid(id: number): void; +} + +// 具体的克隆人类 +class CloneTrooperA implements CloneTrooper { + private id: number; + constructor(id: number) { + this.id = id; + } + + clone(): CloneTrooper { + console.log(`克隆人A-${this.id}号正在克隆...`); + return new CloneTrooperA(this.id); + } + + fight(): void { + console.log(`克隆人A-${this.id}号准备战斗!`); + } + + setid(id: number): void { + this.id = id; + } +} +class CloneTrooperB implements CloneTrooper { + private id: number; + constructor(id: number) { + this.id = id; + } + + clone(): CloneTrooper { + console.log(`克隆人B-${this.id}号正在克隆...`); + return new CloneTrooperB(this.id); + } + + fight(): void { + console.log(`克隆人B-${this.id}号准备战斗!`); + } + + setid(id: number): void { + this.id = id; + } +} + +(function () { + console.log("========= 原型模式 ========="); + // 创建克隆人A原型 + const prototypeA: CloneTrooper = new CloneTrooperA(0); + prototypeA.fight(); + const cloneA1 = prototypeA.clone(); + cloneA1.setid(1); + cloneA1.fight(); + const cloneA2 = cloneA1.clone(); + cloneA2.setid(2); + cloneA2.fight(); + + // 创建克隆人B原型 + const prototypeB: CloneTrooper = new CloneTrooperB(0); + prototypeB.fight(); + const cloneB1 = prototypeB.clone(); + cloneB1.setid(1); + cloneB1.fight(); + const cloneB2 = cloneB1.clone(); + cloneB2.setid(2); + cloneB2.fight(); + + console.log("\n======= 原型模式结束 ======="); +})(); diff --git a/ts/src/singleton/index.ts b/ts/src/singleton/index.ts new file mode 100644 index 0000000..5be713b --- /dev/null +++ b/ts/src/singleton/index.ts @@ -0,0 +1,34 @@ +/* +实例 +汤宝宝混穿到了泰拉世界,并成为了泰拉联邦的唯一统治者。人类只有一个帝皇! +*/ + +class Emperor { + private static instance: Emperor; + readonly name: string; + static getInstance(name: string, announce: string): Emperor { + console.log(announce); + if (!this.instance) { + this.instance = new Emperor(name, announce); + } + return this.instance; + } + + private constructor(name: string, announce: string) { + this.name = name; + } +} + +(function () { + console.log("========= 单例模式 ========="); + const emperor1 = Emperor.getInstance("汤宝宝", "泰拉联邦的帝皇诞生了!"); + console.log(`帝皇的名字是:${emperor1.name}!`); + const emperor2 = Emperor.getInstance("王二狗", "泰拉联邦的帝皇又一次诞生了!"); + console.log(`帝皇的名字是:${emperor2.name}!`); + + if (emperor1 === emperor2) { + console.log(`泰拉只有一个帝皇:${emperor1.name}!\n`); + } + + console.log("======= 单例模式结束 ======="); +})();