C++_设计模式

news/2025/10/15 23:14:16/文章来源:https://www.cnblogs.com/hyt19911004/p/19144477

单例模式

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

  • 饿汉模式

    饿汉模式是在程序启动时就创建实例,因此不存在线程安全问题,但可能会造成资源浪费,特别是当单例对象的初始化代价较高或程序中没有频繁使用该对象时。

    1. 构造函数私有化,这样用户就不能任意定义该类型的对象了
    2. 定义该类型唯一的对象
    3. 通过一个static静态成员方法返回唯一的对象实例
    • #include <iostream>class SingletonHungry {
      private:static SingletonHungry* instance;SingletonHungry() {} // 私有构造函数public:static SingletonHungry* getInstance() {return instance;}
      };// 初始化静态成员
      SingletonHungry* SingletonHungry::instance = new SingletonHungry();int main() {SingletonHungry* s1 = SingletonHungry::getInstance();SingletonHungry* s2 = SingletonHungry::getInstance();// s1 和 s2 指向同一个实例std::cout << (s1 == s2) << std::endl; // 输出 1 表示是同一个实例return 0;
      }
  • 懒汉设计模式

    • #include <iostream>//懒汉式单例设计模式
      class Single
      {
      public://3. 获取类的唯一实例对象的接口方法static Single* getInstacne() { std::cout << "hello codechen,你成功的调用了一次构造函数" << char(10);if (instance == nullptr){std::cout << "在这里对instance进行了初始化" << char(10);instance = new Single();}return instance;}
      private://2. 定义一个唯一的类的实例化的对象,为指针static Single* instance;//1. 构造函数的私有化,不能够自己主动的去调用构造函数
          Single(){//在实际的项目中,构造函数可能会需要做很多的工作//比如说对一些成员变量的初始化,对一些数据的读取等等
      }Single(const Single&) = delete;Single& operator = (const Single&) = delete;
      };
      Single* Single::instance = nullptr;int main()
      {Single* ptr1 = Single::getInstacne();Single* ptr2 = Single::getInstacne();Single* ptr3 = Single::getInstacne();delete ptr1;delete ptr2;delete ptr3;return 0;
      }

工厂模式

  • 简单工厂模式

    • namespace _namespace1
      {class Monster{public:Monster(int life, int magic, int attack) :m_life(life), m_magic(magic), m_attack(attack) {}virtual ~Monster()  // 基类 析构 虚方法
              {}protected:int m_life;int m_magic;int m_attack;};class M_Undead : public Monster{public:M_Undead(int life, int magic, int attack) : Monster(life,magic, attack) {cout << "亡灵类动物" << endl;}};class M_Element : public Monster{public:M_Element(int life, int magic, int attack) : Monster(life, magic, attack) {cout << "元素类动物" << endl;}};class M_Mechanic : public Monster{public:M_Mechanic(int life, int magic, int attack) : Monster(life, magic, attack) {cout << "机械类动物" << endl;}};// 简单工厂模式class MonsterFactor{public:Monster * createMonster(string strmontype){Monster *ptrobj = nullptr;if (strmontype == "a"){ptrobj = new M_Undead(300, 100, 100);}else if (strmontype == "b"){ptrobj = new M_Element(300, 100, 100);}else if (strmontype == "c"){ptrobj = new M_Mechanic(300, 100, 100);}return ptrobj;}};}
      void test2()
      {//2  简单工厂模式的实现思路:使用工厂类可以实现创建怪物的代码,用户在创建时候,与具体的类对象要实现的逻辑代码隔离。
          _namespace1::MonsterFactor fac;_namespace1::Monster *m1 = fac.createMonster("a");_namespace1::Monster *m2 = fac.createMonster("b");_namespace1::Monster *m3 = fac.createMonster("c");
      实例化一个工厂对象,然后通过向工厂中传递对应的标识来创建对象。/*亡灵类动物元素类动物机械类动物*/
      }
    • 利弊分析

      • 开闭原则:代码的扩展性问题:对扩展开发,对修改关闭。当增加新功能,不应该通过修改已经存在的代码,比如在createMonster()中增加if else(), 而是应该通过扩展代码比如增加新类,增加新成员函数来进行扩展。假如上边要增加100个怪物类型,就要增加100个 if else(),这样的做法不可取,如果只增加几个,这样方法也可以,所以应该在代码的可读性和可扩展性之间做出权衡
  • 工厂方法模式

  工厂方法模式简称工厂模式或多态工厂模式;与简单工厂模式比,灵活性更强,实现也更加复杂,一如更多的新类。每一个工厂类对应了怪物类,比如亡灵类对应的工厂为亡灵工厂类。工厂模式:修改代码不如增加代码好,符合开闭原则。

    • namespace _sp1
      {// 怪物类父类class CMonster{public:CMonster(int life,int maigc,int attack):m_life(life),m_magic(maigc), m_attack(attack){}protected:int m_life;int m_magic;int m_attack;};// 亡灵类class CUnded : public CMonster{public:CUnded(int life, int maigc, int attack) :CMonster(life, maigc, attack){cout << "亡灵类来到世界" << endl;}private:};// 元素类class CEle : public CMonster{public:CEle(int life, int maigc, int attack) :CMonster(life, maigc, attack){cout << "元素类来到世界" << endl;}private:};// 机械类class CMecanical : public CMonster{public:CMecanical(int life, int maigc, int attack) :CMonster(life, maigc, attack){cout << "机械类来到世界" << endl;}};// 简单工厂模式:创建一个工厂类,在工厂类中返回对应的 怪物类;// 工厂方法// 1 创建一个工厂基类;class CFactorMonster{public:virtual CMonster * createMonster() = 0;virtual ~CFactorMonster(){}};// 2 创建每个怪物的工厂class CFactorUnded : public CFactorMonster{public:virtual CMonster * createMonster(){CMonster *ptmp = new CUnded(200,300,400);return ptmp;}};class CFactorCEle : public CFactorMonster{public:virtual CMonster * createMonster(){CMonster *ptmp = new CEle(200, 300, 400);  // 多态return ptmp;}};// 创建一个全局方法CMonster *GlobalCreateMonster(CFactorMonster *factory){return factory->createMonster(); // 多态
              }
      }
      void test2()
      {// 先 创建一个工厂父类;由于每个工厂具有固定的步骤,所以有工厂父类;_sp1::CFactorMonster *p = new _sp1::CFactorUnded();_sp1::CMonster *pp = p->createMonster();_sp1::CFactorMonster *p2 = new _sp1::CFactorCEle();_sp1::CMonster *pp2 = p2->createMonster();// 工厂模式创建了一个工厂父类,在此基础上,又增加了每个怪物对应的工厂;// 与简单工厂模式比,比之前的复杂,但是灵活性更强,实现了 开闭原则,付出的代价是新增加了每个怪物的工厂类;// 
      }
  • 抽象工厂模式

    • namespace _nsp1
      {// 怪物类父类class CMonster{public:CMonster(int life, int maigc, int attack) :m_life(life), m_magic(maigc), m_attack(attack){}protected:int m_life;int m_magic;int m_attack;};/// 下面分别实现这9个类别,每个怪物类都继承自怪物父类// 城镇亡灵类class CMonsterTownUndead : public CMonster{public:CMonsterTownUndead(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个城镇亡灵类型怪物来到了这个世界" << endl;}};// 城镇元素类class CMonsterTownElement : public CMonster{public:CMonsterTownElement(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个城镇元素类型怪物来到了这个世界" << endl;}};// 城镇机械类class CMonsterTownMechanic : public CMonster{public:CMonsterTownMechanic(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个城镇机械类型怪物来到了这个世界" << endl;}};/// 山脉类// 山脉亡灵类class CMonsterMaintainUndead : public CMonster{public:CMonsterMaintainUndead(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个山脉亡灵类型怪物来到了这个世界" << endl;}};// 山脉元素类class CMonsterMaintainElement : public CMonster{public:CMonsterMaintainElement(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个山脉元素类型怪物来到了这个世界" << endl;}};// 山脉机械类class CMonsterMaintainMechanic : public CMonster{public:CMonsterMaintainMechanic(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个山脉机械类型怪物来到了这个世界" << endl;}};/// 沼泽类// 沼泽亡灵类class CMonsterMarshUndead : public CMonster{public:CMonsterMarshUndead(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个沼泽亡灵类型怪物来到了这个世界" << endl;}};// 沼泽元素类class CMonsterMarshElement : public CMonster{public:CMonsterMarshElement(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个沼泽元素类型怪物来到了这个世界" << endl;}};// 沼泽机械类class CMonsterMarshMechanic : public CMonster{public:CMonsterMarshMechanic(int life, int magic, int attack) : CMonster(life, magic, attack){cout << "一个沼泽机械类型怪物来到了这个世界" << endl;}};/// 创建工厂class CMonsterFactory{public:virtual CMonster *createMonsterUndead() = 0;virtual CMonster *createMonsterElement() = 0;virtual CMonster *createMonsterMechanic() = 0;virtual ~CMonsterFactory(){}};// 城镇类工厂:一个工厂能生产一个产品族class CMonsterFactoryTown : public CMonsterFactory{virtual CMonster *createMonsterUndead(){return new CMonsterTownUndead(100, 100, 100);}virtual CMonster *createMonsterElement(){return new CMonsterTownElement(100, 100, 100);}virtual CMonster *createMonsterMechanic(){return new CMonsterTownMechanic(100, 100, 100);}};// 山脉类怪物工厂class CMonsterFactoryMaintain : public CMonsterFactory{virtual CMonster *createMonsterUndead(){return new CMonsterMaintainUndead(100, 100, 100);}virtual CMonster *createMonsterElement(){return new CMonsterMaintainElement(100, 100, 100);}virtual CMonster *createMonsterMechanic(){return new CMonsterMaintainMechanic(100, 100, 100);}};// 沼泽类怪物工厂class CMonsterFactoryMarsh : public CMonsterFactory{virtual CMonster *createMonsterUndead(){return new CMonsterMarshUndead(100, 100, 100);}virtual CMonster *createMonsterElement(){return new CMonsterMarshElement(100, 100, 100);}virtual CMonster *createMarshMechanic(){return new CMonsterMaintainMechanic(100, 100, 100);}};}int main()
      {_nsp1::CMonsterFactory *pc = new _nsp1::CMonsterFactoryTown();_nsp1::CMonster *pM1 = pc->createMonsterUndead();_nsp1::CMonster *pM2 = pc->createMonsterMechanic();_nsp1::CMonster *pM3 = pc->createMonsterElement();/*一个城镇亡灵类型怪物来到了这个世界一个城镇机械类型怪物来到了这个世界一个城镇元素类型怪物来到了这个世界    */system("pause");return 0;
      }

       

 

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

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

相关文章

数据库查询通信开销降低97%的技术方案

研究人员提出了一种新的数据库表分布方法,通过分析查询数据识别涉及最大数据传输的连接属性作为分布键,在实验中使多表查询的通信开销降低了80%-97%。如何将数据库查询的通信开销降低高达97% 某中心的研究人员描述了…

人生的底色

人生的底色是孤独的,孤独的出生,孤独的生活,孤独的死去,生命中的每一个人终究只会伴你走过一段旅程,或长或短,或开心或痛苦,但孤独却会伴随你的一生。

差分操作正确性证明

差分操作正确性证明 本文是作者因题目写差分写挂了后随手总结的。 定义 对于一个长度为 \(n\) 的数组 \(a\),定义其差分数组为 \(p\),且 \(\forall 1\le i\le n,p_i=a_i-a_{i-1}(a_0=0)\)。 转化回原数列 给些式子就…

ansible安装脚本

ansible安装脚本#!/usr/bin/env bash # # 通用 Ansible 安装脚本 # 支持多种方式安装(yum/apt/pip/source) # 支持 root 和 普通用户 # 支持自定义版本(默认 2.9.27)set -eANSIBLE_VERSION=${1:-2.9.27} # 默认…

详细介绍:【笔记】介绍 WPF XAML 中 Binding 的 StringFormat详细功能

详细介绍:【笔记】介绍 WPF XAML 中 Binding 的 StringFormat详细功能pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: &…

CF2143D2

给定长度为 \(n(n \le 2000)\) 的序列 \(a\),询问有多少个子序列满足不存在长度 \(\ge 3\) 的下降子序列。 显然可以 DP,令 \(dp_{i, j, k}\) 表示前 \(i\) 个数组成的子序列,最大值为 \(j\),长度为 \(2\) 的下降…

结果(Results)和结论 (Conclusion)的联系与区别

学术论文中结果(Results)和结论 (Conclusion)的联系与区别维度 结果 (Results) 结论 (Conclusion)联系 结论基于结果。结论必须以结果的客观发现为基础,不能无中生有。区别 事实呈现,描述“是什么”(What)。 事实的…

【训练技巧】PyTorch多卡训练模型DistributedDataParallel和DataParallel设置方法详解及分布式训练命令解释 - 实践

【训练技巧】PyTorch多卡训练模型DistributedDataParallel和DataParallel设置方法详解及分布式训练命令解释 - 实践pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; …

20251015

今天上了离散数学课,然后收获了非常多的知识,接着又上了马克思原理课,今天总结下来就是非常的收获,然后中午经过一个舒爽的午睡以后,直接完成英语作业,读了单词剪辑了视频作业,非常的满意,然后还写了算法与数据…

java date 初始化指定时分秒及比较日期大小

java date 初始化指定时分秒及比较日期大小java date 初始化指定时分秒及比较日期大小Date now = new Date();/*** 注意:使用new Date(year, month, date)构造方法时,年份是绝对的年份(比如1999),月份是从0开始的…

软件工程学习日志2025.10.15

今日核心成果 完成了EIMS系统三大核心窗口的视觉统一与体验优化,实现了从"功能可用"到"体验优雅"的重要跨越。 ✨ 界面焕新:细节中的专业感全局视觉语言统一• 字体系统:全平台采用Microsoft Y…

实用指南:玳瑁的嵌入式日记---0929(ARM--ADC)

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

C++篇:007

C++篇:007$(".postTitle2").removeClass("postTitle2").addClass("singleposttitle");C++篇:007.C++20常用新特性 一、模块 模块是一个用于在翻译单元间分享声明和定义的语言特性。它…

C++篇:006

C++篇:006$(".postTitle2").removeClass("postTitle2").addClass("singleposttitle");C++篇:006.C++17常用新特性 一、折叠表达式 C++17中引入了折叠表达式,主要是为了方便模板编程,…

C++篇:005

C++篇:005$(".postTitle2").removeClass("postTitle2").addClass("singleposttitle");C++篇:005.C++11常用新特性 一、auto 在新标准中,auto的功能变为类型推断,通知编译器去根据初…

C++篇:004

C++篇:004$(".postTitle2").removeClass("postTitle2").addClass("singleposttitle");C++篇:004.综合案例 基于字符串的IO操作 1.iostream istream 读取 ostream 写入 iostream 读写 …

轻量级ChatGPT克隆版nanochat技术解析

某知名AI研究员发布开源项目nanochat,提供完整的ChatGPT风格模型训练与推理流程。该项目包含8000行代码,涵盖分词器训练、Transformer预训练、监督微调及强化学习等关键技术环节。轻量级ChatGPT克隆版nanochat技术解…

10.15 —— 2020icpc上海D

临近一个月得知区域赛有了名额,可能也不算是好消息,大概率会延续去年打铁的经历。但不管怎样,我都会全力以赴,就算失败,我也会坦然地告诉自己尽力了,没有什么遗憾。 紧急进行一个小规划:争取每天练一道铁铜牌区…

[QOJ888] Travel around China 题解

存在[QOJ888] Travel around China 题解Petrozavodsk Winter 2021. Day 4. PKU Contest (Common Contest 1)考虑 \(n = 2\),猫树分治,考虑统计所有经过 \(mid\) 的区间,从 \(mid\) 开始跑最短路,处理出区间左右端点…

MySQL面试必考:从入门到精通的20个问题

低级难度问题问题:MySQL和SQL Server有什么区别? 答案:MySQL是一个开源的关系数据库管理系统,而SQL Server是微软开发的一个商业数据库管理系统。它们在性能、安全性、功能和成本方面有所不同。 案例: -- MySQL 分…