设计模式-01 设计模式单例模式

news2025/1/9 15:51:20
设计模式-01 设计模式单例模式

目录

设计模式-01 设计模式单例模式

1定义

2.内涵

3.使用示例

4.具体代码使用实践

5.注意事项

6.最佳实践

7.总结


1 定义


单例模式是一种设计模式,它确保一个类只能被实例化一次。它通过在类内部创建类的唯一实例并提供一个全局访问点来实现这一点。


优点:

全局访问:单例对象可以从应用程序的任何地方访问。
资源节约:它只创建一个对象,从而节省了内存和资源。
线程安全性:如果单例对象正确实现,它可以是线程安全的,这意味着它可以在多线程环境中安全地使用。


2.内涵

单例模式在 C++ 设计模式中具有以下内涵:

封装:单例类的内部状态和实现细节对客户端代码是隐藏的。这使你可以自由地更改类的实现,而无需影响使用它的代码。
全局访问:单例对象可以在应用程序的任何地方访问,这使得它非常适合存储全局状态或提供公共服务。
资源管理:由于单例模式确保只创建一个对象,因此它可以帮助管理资源,例如数据库连接或文件句柄。

3.使用示例

单例模式,有很多种实现方式,下面是几种实现方式的介绍。

延迟加载

class Singleton {
private:
    static Singleton* instance;
    Singleton() {}

public:
    static Singleton* getInstance() {
        if (instance == nullptr) {
            instance = new Singleton();
        }
        return instance;
    }
};


饿汉式

class Singleton {
private:
    static Singleton* instance = new Singleton();
    Singleton() {}

public:
    static Singleton* getInstance() {
        return instance;
    }
};

C++11 实现单例模式代码

class Singleton {
private:
    Singleton() {}  // 私有构造函数防止直接实例化
    Singleton(const Singleton&) = delete;  // 私有拷贝构造函数防止复制
    Singleton& operator=(const Singleton&) = delete;  // 私有赋值运算符防止赋值

    static Singleton* instance;  // 静态成员变量存储单例实例

public:
    static Singleton& getInstance() {
        // 双重检查锁定,确保线程安全
        if (instance == nullptr) {
            std::lock_guard<std::mutex> lock(mutex);
            if (instance == nullptr) {
                instance = new Singleton();
            }
        }
        return *instance;
    }

private:
    static std::mutex mutex;  // 互斥锁用于线程安全
};

// 在类外初始化静态成员变量
Singleton* Singleton::instance = nullptr;
std::mutex Singleton::mutex;

4.具体代码使用实践
#include <iostream>
 
class Singleton {
public:
    // Static method to access the singleton instance
    static Singleton& getInstance()
    {
        // If the instance doesn't exist, create it
        if (!instance) {
            instance = new Singleton();
        }
        return *instance;
    }
 
    // Public method to perform some operation
    void someOperation()
    {
        std::cout
            << "Singleton is performing some operation."
            << std::endl;
    }
 
    // Delete the copy constructor and assignment operator
    Singleton(const Singleton&) = delete;
    Singleton& operator=(const Singleton&) = delete;
 
private:
    // Private constructor to prevent external instantiation
    Singleton()
    {
        std::cout << "Singleton instance created."
                  << std::endl;
    }
 
    // Private destructor to prevent external deletion
    ~Singleton()
    {
        std::cout << "Singleton instance destroyed."
                  << std::endl;
    }
 
    // Private static instance variable
    static Singleton* instance;
};
 
// Initialize the static instance variable to nullptr
Singleton* Singleton::instance = nullptr;
 
int main()
{
    // Access the Singleton instance
    Singleton& singleton = Singleton::getInstance();
 
    // Use the Singleton instance
    singleton.someOperation();
 
    // Attempting to create another instance will not work
    // Singleton anotherInstance; // This line would not
    // compile
 
    return 0;
}

5.注意事项


C++11 实现单例模式的注意事项和潜在问题:

1. 线程安全性:

确保单例类的实现是线程安全的,以避免并行访问时出现数据损坏。使用互斥锁或其他同步机制来保护共享数据。


2. 静态局部变量初始化顺序未定义:

在 C++11 中,静态局部变量(例如 Singleton::instance)的初始化顺序是未定义的。为了确保单例类的正确初始化,请使用双重检查锁定模式。


3. 循环引用和内存泄漏:

如果单例类持有其他对象的引用,请确保这些引用不会导致循环引用并导致内存泄漏。可以使用智能指针或弱引用来管理引用。


4. 异常安全性:

单例类的构造函数应该抛出异常安全,这意味着在构造函数抛出异常后,单例类的状态应该保持有效。可以使用 RAII 技术来实现异常安全性。


5. 过度使用:

避免过度使用单例模式。只在需要全局访问和资源管理的情况下才使用它。过度使用单例模式可能会导致设计僵化和测试困难。

6.最佳实践
  • 使用双重检查锁定:这是一种可靠的方法来确保线程安全的单例实现。
  • 使用 RAII 技术:这可以确保在异常情况下正确清理资源。
  • 仔细管理引用:使用智能指针或弱引用来避免循环引用和内存泄漏。
  • 仅在必要时使用单例模式:考虑其他设计模式,例如工厂模式或依赖注入,以实现全局访问和资源管理。
  • 进行彻底的测试:编写测试用例来验证单例实现的正确性和线程安全性。

7.总结

C++11 中的单例模式通过双重检查锁定和 RAII 技术实现线程安全的惰性实例化,确保全局访问和资源管理。在实现上,这比起低版本的来说,预言特性给我们更加灵活的操作性

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

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

相关文章

c#数据库: 10.调用存储过程查询信息,并显示在窗体上

查询女生信息&#xff0c;并将信息显示在窗体上: 原数据表//右键数据库名,新建查询 ------------- 新建查询窗口,添加新建存储过程Procedure_GetGirls1和查询代码如下 : CREATE PROCEDURE dbo.Procedure_GetGirls1 /*存储过程名称*/ AS SELECT * f…

变电站自动化控制系统应用案例分析

变电站自动化控制系统介绍 变电站自动化控制系统用于大中型企业变电站项目&#xff0c;这类企业变压器多&#xff0c;日耗电量大。把多个变压器集中到一个电器平台上&#xff0c;集中管理分析&#xff0c;优化厂区用电管理&#xff0c;从而达到集中控制、集中分析、集中管理的…

【Unity 自定义组件】

想了解更多游戏开发知识,可以扫描下方二维码,免费领取游戏开发4天训练营课程 在Unity中&#xff0c;自定义组件&#xff08;Custom Component&#xff09;是指开发者根据游戏的具体需求编写的C#脚本&#xff0c;这些脚本可以附加到游戏对象&#xff08;GameObject&#xff09;…

如何远程访问服务器?

在现代信息技术的快速发展下&#xff0c;远程访问服务器已成为越来越多用户的需求。远程访问服务器能够让用户随时随地通过网络连接服务器&#xff0c;实现数据的传输和操作。本文将介绍远程访问服务器的概念&#xff0c;以及一种广泛应用于不同行业的远程访问解决方案——【天…

标准汽车试验铁地板的技术要求

在现代科技化发展的工作中&#xff0c;试验平台被广泛使用。铸铁试验平台&#xff08;试验铁地板&#xff09;又叫试验工作平台&#xff0c;听名字大家也不难想象出来这是一款带有箱式体的台面&#xff0c;这是一种有长方形或者圆形又或者正方形的试验工作台。 铸铁试验平台&a…

QT5制做两个独立窗口

目录 增加第二个窗口 主窗口文件添加一个私有成员为子窗口 定义两个槽函数和 关联按钮和子窗口和主窗口 添加子窗口成员 子窗口处理函数 补充回顾 增加第二个窗口 1、 2、 3 主窗口文件添加一个私有成员为子窗口 在mainwidget.h文件 同时添加两个槽&#xff1b;来处理…

(成品论文22页)24深圳杯数学建模A题1-4问完整代码+参考论文重磅更新!!!!

论文如下&#xff1a; 基于三球定位的多个火箭残骸的准确定位 针对问题一&#xff1a;为了进行单个残骸的精确定位&#xff0c;确定单个火箭残骸发生音爆 时的精确位置和时间&#xff0c;本文基于三球定位模型&#xff0c;考虑到解的存在性和唯一性&#xff0c; 选取了四个监测…

AI大模型日报#0430:疑似GPT4.5模型刷屏、上交实现「蛋白质功能定向进化」、微软紧急撤回WizardLM-2

导读&#xff1a; 欢迎阅读《AI大模型日报》&#xff0c;内容基于Python爬虫和LLM自动生成。目前采用“文心一言”生成了今日要点以及每条资讯的摘要。 《AI大模型日报》今日要点&#xff1a; 在AI大模型领域&#xff0c;多项研究进展和行业应用动态引发关注。一夜之间&#x…

第9篇:创建Nios II工程之读取Switch的值<二>

Q&#xff1a;上一期我们完成了Quartus硬件工程部分&#xff0c;本期我们创建Nios II软件工程这部分。 A&#xff1a;创建完BSP和Nios II Application之后&#xff0c;在source文件main.c中添加代码&#xff1a;system.h头文件中新增了Switch PIO IP的硬件信息&#xff0c;包括…

气象数据nc数据矢量化处理解析及可视化

气象数据可视化是将气象学领域中复杂的数据集转化为图形或图像的过程&#xff0c;以直观展示天气现象、气候模式、趋势和预报结果。气象数据的可视化技术广泛应用于科学研究、气象预报、航空、航海、农业生产、灾害预警系统、城市规划、公众服务等领域。以下是一些关键的气象数…

Stability AI 推出稳定音频 2.0:为创作者提供先进的 AI 生成音频

概述 Stability AI 的发布再次突破了创新的界限。这一尖端模型以其前身的成功为基础&#xff0c;引入了一系列突破性的功能&#xff0c;有望彻底改变艺术家和音乐家创建和操作音频内容的方式。 Stable Audio 2.0 代表了人工智能生成音频发展的一个重要里程碑&#xff0c;为质量…

口袋实验室--使用AD2学习频谱参数测试

目录 1. 简介 2. 频谱相关参数 2.1 频谱相关基本概念 2.1.1 采样时间间隔 2.1.2 采样频率 2.1.3 采样点数 2.1.4 采样时间长度 2.1.5 谱线数 2.1.6 奈奎斯特频率 2.1.7 频谱分辨率 2.1.8 最高分析频率 2.1.9 频谱泄露 2.2 窗函数 2.2.1 AD2的窗函数 2.2.2 测试矩…

Cesium 3dTileset 支持 uv 和 纹理贴图

原理: 使用自定义shader实现uv自动计算 贴图效果: uv效果:

链表算法题总结

链表作为一个基础的数据结构&#xff0c;在开发中经常被使用。 链表往往使用如下的数据结构来表示&#xff0c;struct node 表示链表中的一个节点&#xff0c;data 表示节点的数据&#xff1b;next 表示这个节点指向的下一个节点&#xff0c;如果是链表的尾节点&#xff0c;那…

Vulnhub-DIGITALWORLD.LOCAL: VENGEANCE渗透

文章目录 前言1、靶机ip配置2、渗透目标3、渗透概括 开始实战一、信息获取二、smb下载线索三、制作字典四、爆破压缩包密码五、线索分析六、提权&#xff01;&#xff01;&#xff01; Vulnhub靶机&#xff1a;DIGITALWORLD.LOCAL: VENGEANCE ( digitalworld.local: VENGEANCE …

服务器部署开源大模型完整教程 Ollama+Llama3+open-webui

前言 最近大语言模型大火&#xff0c;正好最近打比赛可能会用得上LLMs&#xff0c;今天就在学校的服务器上面进行一次部署。这样之后就可以直接在内网里面使用学校的LLMs了。 介绍 Ollama&#xff1a;一款可以让你在本地快速搭建大模型的工具 官网&#xff1a;https://olla…

串口协议(例如usart,iic,spi)基础概念汇总

文章目录 同步&#xff0c;异步同步通信&#xff1a;异步通信&#xff1a; 串行&#xff0c;并行串行&#xff1a;并行&#xff1a; 全双工&#xff0c;半双工&#xff0c;单工单工&#xff1a;半双工&#xff1a;全双工&#xff1a; 电平信号&#xff0c;差分信号电平信号&…

Flutter笔记:Widgets Easier组件库(2)阴影盒子

Flutter笔记 Widgets Easier组件库&#xff08;2&#xff09;&#xff1a;阴影盒子 - 文章信息 - Author: 李俊才 (jcLee95) Visit me at CSDN: https://jclee95.blog.csdn.netMy WebSite&#xff1a;http://thispage.tech/Email: 291148484163.com. Shenzhen ChinaAddress o…

[软件工具]批量根据文件名查找PDF文件复制到指定的地方,如何批量查找文件复制,多个文件一起查找复制

多个文件目录下有多个PDF, 如何根据文件名一个清单&#xff0c;一次性查找多个PDF复制保存 如图所示下面有7个文件夹&#xff0c;每个文件夹里面有几百上千PDF文件 如何从上千个PDF文件中一次性快速找到我们要的文件呢 &#xff1f; 我们需要找到文件名是这样的PDF&#xff0…

如何删除BigKey1

方案一 拆分为string类型 keyvalueid:0value0..........id:999999value999999 存在的问题&#xff1a; string结构底层没有太多内存优化&#xff0c;内存占用较多 想要批量获取这些数据比较麻烦 方案二 拆分为小的hash&#xff0c;将 id / 100 作为key&#xff0c; 将id …