设计模式之单例模式入门介绍
一、设计模式概念
设计模式是被广泛使用的软件开发中的一种解决方案,它提供了一套被验证过的、可重用的设计思想,帮助开发人员更加高效地开发出可维护、易扩展的软件系统。
设计模式可以分为三类:创建型模式、结构型模式和行为型模式。
1.1 创建型模式
创建型模式用于描述对象的创建过程,它的目的是封装对象的创建过程,从而降低系统的耦合度,并且能够更加灵活地创建对象。创建型模式包括单例模式、工厂方法模式、抽象工厂模式、建造者模式和原型模式等。
1.2 结构型模式
结构型模式用于描述如何将类或对象按某种布局组成更大的结构,它涉及到接口和类的组合。结构型模式包括适配器模式、桥接模式、组合模式、装饰者模式、外观模式、享元模式和代理模式等。
1.3 行为型模式
结构型模式用于描述如何将类或对象按某种布局组成更大的结构,它涉及到接口和类的组合。结构型模式包括适配器模式、桥接模式、组合模式、装饰者模式、外观模式、享元模式和代理模式等。
二、单例模式概念
单例模式是一种创建型设计模式,它保证一个类只有一个实例,并提供一个全局访问点。
1.将构造函数私有化:将类的构造函数设为私有,这样外部就无法通过构造函数来创建该类的对象。
2.提供一个静态成员变量来保存唯一实例:在该类中定义一个静态成员变量,用于保存该类的唯一实例。
3.提供一个静态方法来获取唯一实例:在该类中定义一个静态方法,用于获取该类的唯一实例。在该方法中,判断静态成员变量是否为空,如果为空,则创建一个新的对象并赋值给静态成员变量,然后返回该静态成员变量。
4.禁止复制构造函数和赋值运算符:为了避免从已有对象派生出新的对象,需要将复制构造函数和赋值运算符定义为私有或删除函数。
通过上述方法可以使单例类只有一个对象,全局只有一个实例对象存在,通过静态接口来获取该实例
2.1 饿汉模式:
饿汉模式就像有种饿叫做你妈妈/奶奶觉得你饿,不管你真饿假饿 我都把饭给你做好,饿汉模式也一样,我直接把单例对象给你初始化好,完了你直接用就可以了
代码示例:
class Singleton {
public:static Singleton* getInstance() { //获取单例对象的静态接口return instance;}
private:static Singleton* instance;//静态对象Singleton() {}//构造、拷贝构造、赋值设置为私有Singleton(const Singleton&) = delete;Singleton& operator=(const Singleton&) = delete;
};Singleton* Singleton::instance = new Singleton(); //类加载之后就直接初始化,饿汉模式
2.2 懒汉模式:
懒汉模式就是比较懒,有人要获取单例对象我才来实例化,踢一脚走一步的那种
代码示例:
class Singleton {
public:static Singleton* getInstance() { //获取单例对象的静态接口if (instance == nullptr)//如果单例对象没有初始化,则进行初始化{instance = new Singleton();}return instance;}
private:static Singleton* instance;//静态对象Singleton() {}//构造、拷贝构造、赋值设置为私有Singleton(const Singleton&) = delete;Singleton& operator=(const Singleton&) = delete;
};
Singleton*Singleton::instance = nullptr; //初始化为 nullptr
有了代码,那当然要试一试单例模式怎么玩,验证一下是不是真的只有一个单例对象:

可以看到,单例对象是唯一的
2.3 单例模式验证测试
2.3.1 饿汉模式
代码示例:
#include<iostream>
using namespace std;class Singleton {
public:static Singleton* getInstance() { //获取单例对象的静态接口return instance;}void Print(){cout << "hello world" << endl;}
private:static Singleton* instance;//静态对象Singleton() {}//构造、拷贝构造、赋值设置为私有Singleton(const Singleton&) = delete;Singleton& operator=(const Singleton&) = delete;
};Singleton* Singleton::instance = new Singleton(); //类加载之后就直接初始化,饿汉模式
int main()
{//1.构造对象试试Singleton sin;//报错构造函数私有化,无法在类外实例化出对象return 0;
}
那么如何去调用这个单例类里面的方法呢?
//调用静态方法获取单例对象(单例对象指针) 然后调用单例类中的成员函数
Singleton::getInstance()->Print();
运行结果:

三、单例模式是线程安全的吗?
我们考虑这样一个场景,两个线程,懒汉模式下,同时去获取这个单例对象,那么在获取单例对象之前,都是nullptr ,那么都会同时去 new 一个单例对象,导致会创建多个单例对象,那么就无法实现单例模式单例对象唯一的特点
我们可以通过加锁来解决该问题:
#include <mutex>class Singleton {
private:static Singleton* instance;static std::mutex mtx;Singleton() {}public:static Singleton* getInstance() {if (instance == nullptr) { // 第一次检查是否为空std::lock_guard<std::mutex> lock(mtx); // 加锁保证线程安全if (instance == nullptr) { // 第二次检查是否为空instance = new Singleton();}}return instance;}// 禁止拷贝构造函数和赋值运算符Singleton(const Singleton&) = delete;Singleton& operator=(const Singleton&) = delete;
};Singleton* Singleton::instance = nullptr;
std::mutex Singleton::mtx;
当然了 饿汉模式是线程安全的,因为单例类对象在类加载完就进行了实例化,通过静态接口获取单例对象时直接获取即可,无需初始化。
相关文章:
设计模式之单例模式入门介绍
一、设计模式概念 设计模式是被广泛使用的软件开发中的一种解决方案,它提供了一套被验证过的、可重用的设计思想,帮助开发人员更加高效地开发出可维护、易扩展的软件系统。 设计模式可以分为三类:创建型模式、结构型模式和行为型模式。 1.1…...
RHCE 作业三
1.基于域名访问网站 [rootserver ~]# setenforce 0 [rootserver ~]# systemctl stop firewalld [rootserver ~]# systemctl disable firewalld [rootserver ~]# yum install httpd -y [rootserver ~]# systemctl start httpd [rootserver ~]# syst…...
90.qt qml-Table表格组件(支持表头表尾固定/自定义颜色/自定义操作按钮/插入排序)
众所周知,qml table在目前版本还很废,qt5的table完全就没法用,在之前章节就写过: 88.qt qml-TableView学习(一)_诺谦的博客-CSDN博客 所以本章便参考VUE-Element的Table外观组件实现一个可排序可操作的Table组件. 1.组件介绍 GIF如下所示: 排序支持数字和字符串排序。 …...
android 12.0SystemUI屏蔽某个app的通知
1.概述 在12.0的产品开发中,对于系统的通知部分,要求根据app包名来过滤掉一部分通知,就是在接收到系统通知时,根据包名判断是否需要接收通知的功能,首选要分析通知流程,然后实现功能 2.SystemUI屏蔽某个app的通知相关代码 frameworks\base\packages\SystemUI\src\com\…...
注意力机制(一)SE模块(Squeeze-and-Excitation Networks)论文总结和代码实现
Squeeze-and-Excitation Networks(压缩和激励网络) 论文地址:Squeeze-and-Excitation Networks 论文中文版:Squeeze-and-Excitation Networks_中文版 代码地址:GitHub - hujie-frank/SENet: Squeeze-and-Excitation Ne…...
L2-001 紧急救援(dijkstra算法练习)
作为一个城市的应急救援队伍的负责人,你有一张特殊的全国地图。在地图上显示有多个分散的城市和一些连接城市的快速道路。每个城市的救援队数量和每一条连接两个城市的快速道路长度都标在地图上。当其他城市有紧急求助电话给你的时候,你的任务是带领你的…...
redis问题汇总
redis的优点 读写性能优异。十万/s的量级; 支持数据持久化。AOF,RDB 支持丰富的数据类型; 支持集群,可以实现主从复制,哨兵机制迁移,扩容等 缺点: 因为是基于内存的,所以虽然redis本身有key过期…...
调用华为API实现情感分析
作者介绍 王新华,男,西安工程大学电子信息学院,2022级研究生 研究方向:人工智能与模式识别 电子邮件:996514274qq.com 魏小双,女,西安工程大学电子信息学院,2022级研究生 研究方向…...
C# 静态构造函数
静态构造函数用于初始化任何静态数据,或执行仅需要执行一次的特定操作。在创建第一个实例或引用任何静态成员之前,将自动调用它。 静态构造函数是在构造函数方法前面添加了static关键字之后形成的,并且没有修饰符(public,private),没有参数。…...
【C++】哈希表特性总结及unordered_map和unordered_set的模拟实现
✍作者:阿润菜菜 📖专栏:C 文章目录 前言一、哈希表的特性 - 哈希函数和哈希冲突1 哈希函数2. 哈希冲突 二、闭散列的实现 -- 开放地址法1. 定义数据结构2.insert()3.Find()4. Erase()5.仿函数处理key值不能取模无法映射 --- BKDRHash 三、开…...
Qt在Linux内核中的应用及解析(qtlinux内核)
Qt是跨平台开发的一种工具,尤其适合在Linux内核中的应用开发中使用。Qt能够让开发者在Linux桌面上开发出强大的图形化应用程序,为Linux系统用户提供更加人性化、实用、智能化的服务。本文将从Qt在Linux内核中的应用场景、应用程序开发中的具体使用、以及…...
Xpdf 阅读器源码编译后查看文件中文乱码问题解决
经查阅,是由于缺少中文字体包: 第一步:下载所需要的字体包 下载https://dl.xpdfreader.com/xpdf-t1fonts.tar.gz 包含下载中文字体包(非嵌入字体) http://ftp.gnu.org/gnu/non-gnu/chinese-fonts-truetype/gkai00mp…...
Java - AQS-CountDownLatch实现类(二)
前言 在Java中,AbstractQueuedSynchronizer(简称AQS)是一个用于实现同步器的抽象类,它为实现各种类型的同步器(如锁、信号量等)提供了基本的框架。AQS通过一个双向队列(等待队列)和…...
rsut基础
这篇文章是实战性质的,也就是说原理部分较少,属于经验总结,rust对于模块的例子太少了。rust特性比较多(悲),本文的内容可能只是一部分,实现方式也不一定是这一种。 关于 rust 模块的相关内容&a…...
高压放大器和示波器的关系是什么
高压放大器和示波器是电子工程领域中常见的两种设备,它们在实际的电路设计、测试和分析中都扮演着重要的角色。下面安泰电子将从定义、功能、应用场景等方面为您介绍高压放大器和示波器的关系。 图:ATA-7000系列高压放大器 一、高压放大器的定义及功能 高…...
5个超实用视频素材网站,免费下载~
推荐几个高清无水印的视频素材网站,重点是可以免费下载使用,建议收藏! 菜鸟图库 https://www.sucai999.com/video.html?vNTYxMjky 可以称之为最大素材库,在这里你可以找到设计、办公、图片、视频、音频等各种素材。视频素材就有…...
【NLP模型】文本建模(1)(BoW、N-gram、tf-idf)
目录 一、说明 二、BoW模型产生发展 2.1 产生和历史 2.2 原理介绍 三、具体实现...
Java——网络编程套接字
目录 一、网络编程基础 1.1 为什么需要网络编程?——丰富的网络资源 二、什么是网络编程? 三、网络编程中的基本概念 3.2 请求和响应 3.3 客户端和服务端 常见的客户端服务端模型 四、Socket套接字 五、通信模型 5.1 Java数据报套接字通信模型 5.2 Java流…...
160套小程序源码
源码列表如下: AppleMusic (知乎日报) 微信小程序 d artand 今日更新求职招聘类 医药网 口碑外卖点餐 城市天气 外卖小程序 定位天气 家居在线 微信小程序-大好商城,wechat-weapp 微信小程序的掘金信息流 微信跳一跳小游戏源码 微票源码-demo 急救应急处…...
有效项目进度管理的 10 条规则
项目进度管理是项目中比较关键的方面之一,因为它将决定事情的进展方式、进展速度以及是否会取得进展。换句话说,它可以让你较好地控制项目,帮助你预测不可预测的情况,并使所有相关团队能够高效地协同工作。 以下是有效项目进度管…...
SpringBoot-17-MyBatis动态SQL标签之常用标签
文章目录 1 代码1.1 实体User.java1.2 接口UserMapper.java1.3 映射UserMapper.xml1.3.1 标签if1.3.2 标签if和where1.3.3 标签choose和when和otherwise1.4 UserController.java2 常用动态SQL标签2.1 标签set2.1.1 UserMapper.java2.1.2 UserMapper.xml2.1.3 UserController.ja…...
C++:std::is_convertible
C++标志库中提供is_convertible,可以测试一种类型是否可以转换为另一只类型: template <class From, class To> struct is_convertible; 使用举例: #include <iostream> #include <string>using namespace std;struct A { }; struct B : A { };int main…...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...
【Java_EE】Spring MVC
目录 Spring Web MVC 编辑注解 RestController RequestMapping RequestParam RequestParam RequestBody PathVariable RequestPart 参数传递 注意事项 编辑参数重命名 RequestParam 编辑编辑传递集合 RequestParam 传递JSON数据 编辑RequestBody …...
SpringTask-03.入门案例
一.入门案例 启动类: package com.sky;import lombok.extern.slf4j.Slf4j; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cache.annotation.EnableCach…...
在Ubuntu24上采用Wine打开SourceInsight
1. 安装wine sudo apt install wine 2. 安装32位库支持,SourceInsight是32位程序 sudo dpkg --add-architecture i386 sudo apt update sudo apt install wine32:i386 3. 验证安装 wine --version 4. 安装必要的字体和库(解决显示问题) sudo apt install fonts-wqy…...
Mysql中select查询语句的执行过程
目录 1、介绍 1.1、组件介绍 1.2、Sql执行顺序 2、执行流程 2.1. 连接与认证 2.2. 查询缓存 2.3. 语法解析(Parser) 2.4、执行sql 1. 预处理(Preprocessor) 2. 查询优化器(Optimizer) 3. 执行器…...
安宝特案例丨Vuzix AR智能眼镜集成专业软件,助力卢森堡医院药房转型,赢得辉瑞创新奖
在Vuzix M400 AR智能眼镜的助力下,卢森堡罗伯特舒曼医院(the Robert Schuman Hospitals, HRS)凭借在无菌制剂生产流程中引入增强现实技术(AR)创新项目,荣获了2024年6月7日由卢森堡医院药剂师协会࿰…...
基于IDIG-GAN的小样本电机轴承故障诊断
目录 🔍 核心问题 一、IDIG-GAN模型原理 1. 整体架构 2. 核心创新点 (1) 梯度归一化(Gradient Normalization) (2) 判别器梯度间隙正则化(Discriminator Gradient Gap Regularization) (3) 自注意力机制(Self-Attention) 3. 完整损失函数 二…...
搭建DNS域名解析服务器(正向解析资源文件)
正向解析资源文件 1)准备工作 服务端及客户端都关闭安全软件 [rootlocalhost ~]# systemctl stop firewalld [rootlocalhost ~]# setenforce 0 2)服务端安装软件:bind 1.配置yum源 [rootlocalhost ~]# cat /etc/yum.repos.d/base.repo [Base…...
