单例模式细说

【理论知识】单例模式(懒汉式+饿汉式+枚举) 软件设计模式(Software Design Pattern) 又称设计模式,是一套被反复使用、多数人知晓的、经过分类编目的、代码设计经验的总结。它描述了在软件设计过程中的一些不断重复发生的问题,以及该问题的解决方案。也就是说,它是解决特定问题的一系列套路,是前辈们的代码设计经验的总结,具有一定的普遍性,可以反复使用。其目的是为了提高代码的可重用性、代码的可读性和代码的可靠性。... 阅读详情

背景

单例模式,可以说是最常用的设计模式了,在工程中大量被用到。虽然单例模式比较简单,但是如果单例模式没用好,那也会遇到很多莫名其妙的坑,这里就来讲讲单例模式的一些注意点。

 

单例模式创建对象有分几种情况:

1 局部静态变量, 函数内创建的局部static变量,只创建一次。这种不需要额外的全局变量和成员变量。

2 函数内new 出来的对象,需要根据指针判断是否创建过。这种需要全局变量或者成员变量来保存这个指针。

3 以上二者结合,局部静态的指针,再通过new的方式创建。也不需要额外的变量。

4 boost或其他第三方库提供的单例,如boost::detail::thread::singleton;

5 std::call_once,C++11的标准库中的方式。

 

单例模式如何防止多实例:

一般单例都是拒绝多个实例,所以不允许赋值和拷贝,构造函数一般外部不能直接使用的,即不能直接在外部构造对象。通常可以继承boost::noncopyable,来防止这种情况。或者自己将构造函数、拷贝构造、和赋值操作符定义为私有,或者使用C++11的delete关键字加在函数末尾 如Singleton( const Singleton& ) = delete;防止编译器自动生成这几个函数。

 

单例模式的线程安全:

如果只在主线程用,那可以不加锁,如果多线程用,需要注意多次创建问题。一般多线程使用单例不加锁的话,需要在程序开始时单独初始化,如果别人不小心在之前创建了另外一个线程也用了此单例,可能导致多次创建的问题。

另外,如果单例都在开始时初始化,可能导致性能问题,集中初始化可能占用较多时间。

所以单例最好能加锁确保被人不会误用。最好是加锁的,加锁能真正做到用到才初始化,所谓的懒汉模式。但是加锁又有性能问题,所以有个方法即加锁,性能又高,即在加锁前增加判断,如果创建过了就不加锁了:

 

但是双重检查真的万无一失吗?更深入的研究发现,有时两次检查和加锁的这种方式也不是绝对的线程安全的!因为编译器优化可能导致new的步骤被打乱。

instance = new Singleton()至少包含三个步骤:

1为Singleton分配内存

2在内存中创建Singleton对象

3让实例引用Singleton对象

例如,出于优化原因,处理器可以将步骤重新排序到序列1->3->2。

这样,在第一步骤中将分配内存,而在第二步骤中,实例极有可能是个不完整的实例(还没初始化完成)。如果在那个时候另一个线程试图访问单例,它会比较指针并得到答案为真。所以,另一个线程有一种错觉,即它以为它正在处理一个完整的单例。结果很简单:程序行为未定义。

那有没有线程安全的单例呢?后面会讲到。

 

单例模式代码惯用法:

1 直接在类中增加宏定义,来增加类的GetInstance和ReleaseInstance成员函数。这样做会侵入代码,修改原来的类。还需要注意对象被拷贝的问题。

2 通过继承方式,继承父类的接口。这样不用修改原有的类,也不用担心对象被私自创建与拷贝,因为父类用已经继承了noncopyable。

3 不通过继承,直接通过单例类加模板来使用单例,这种不需要修改原有的类,不过要注意对象被拷贝或私自构造的情况:

typedef boost::detail::thread::singleton<MyClass> MyClassSingleton;

MyClassSingleton::instance();

 

单例模式的懒汉与饿汉模式:

懒汉:故名思义,不到万不得已就不会去实例化类。也就是说在第一次用到类实例的时候才会去实例化;

饿汉:饿了肯定要饥不择食。所以在单例类定义的时候就进行实例化(如全局变量或静态成员变量初始化时直接构造一个)。总结就是,很早初始化,不论后面是否使用。

 

单例模式C++11增强:

旧版C++中不加锁的单例可能被重复创建。在C++11中,支持了线程安全的单例类。

局部的static 静态变量在C++11时多线程情况下依然正确运作,不会被多次构造!

这种单例模式称作Meyers模式,C++11时的最佳选择:

C++11还提供了std::call_once和std::once_flag来实现单例:

 

手教你如何使用Simulink和相关工具箱模拟和实现无人机的多机接力信号中继的建模 扩大通信范围:单架无人机的通信能力有限,通过多机接力的方式可以显著扩展通信覆盖范围。提高可靠性:当某架无人机出现故障或电量不足时,其他无人机可以接管其任务,确保通信不中断。适应复杂环境:在山区、森林等复杂地形中,多机接力可以绕过障碍物,建立稳定的通信链路。使用Communications Toolbox中的模块来模拟无线通信链路。例如,可以使用模块模拟噪声信道,或者使用模块计算信号衰减。matlab深色版本。 阅读详情

相关推荐

保姆级教程:用GROMACS 2022.4的拉伸模拟(SMD)加速蛋白-蛋白组装过程

本文详细介绍了如何使用GROMACS 2022.4的拉伸分子动力学模拟(SMD)技术加速大蛋白组装过程。通过CHARMM36力场和SMD技术,将传统需要数月的蛋白结合过程缩短至数天,大幅提升模拟效率。文章包含参数设计、索引组创建、周期性边界处理等实战技巧,并提供了完整的GPU加速工作流和常见问题解决方案。

weixin_30338481的博客 445

boost的4种单例以及使用方法

boost4种单例及使用方法

山不在高有仙则灵,水不在深有龙则灵 817

Bochs源码分析 - 26:8259中断控制器介绍

前言 现在我们跟着《x86/x64体系探索及编程》来分析17章内容 -- 8259中断控制器。这个是涉及硬件的,很遗憾,除了大学期间使用STM32搞过一个计算器,其余就没多少硬件编程经验,我在淘宝上找了下大概是这个东东。 https://pdos.csail.mit.edu/6.828/2010/readings/hardware/8259A.pdf 上面是8259A的芯片手册,里面讲的还是挺详细的,虽然里面很多东西还是看不太懂,但是结合着《x86/...

WriteAnything_的博客 967

BOOST的Singleton模版详解

首先要说明,这个准确说并不是BOOST的singleton实现,而是BOOST的POOL库的singleton实现。BOOST库中其实有若干个singleton模版,这个只是其中一个。但网上大部分介绍的介绍的BOOST的Singleton实现都是这个,所以大家也就默认了。而且这个的确算是比较特殊和有趣的一个实现。 网上比较有名的文章是这篇《2B程序员,普通程序员和文艺程序员的Singl...

weixin_30823833的博客 283

从C到汇编:单片机汇编语言核心概念迁移指南

本文详细介绍了从C语言迁移到单片机汇编语言的核心概念与实践指南,特别适合嵌入式开发者。文章深入探讨了汇编语言在性能优化、时序控制等方面的独特优势,并提供了变量存储、函数实现、流程控制等关键概念的对应关系,帮助开发者高效掌握汇编编程技巧。

weixin_31887307的博客 346

COMSOL仿真避坑指南:列管反应器模拟中多孔介质与化学反应设置的5个常见错误

本文详细解析了COMSOL仿真中列管反应器模拟的5个常见错误,包括多孔介质模型选择、化学反应接口配置、对流扩散方程处理、薄层热阻设置及网格独立性验证。特别针对多孔介质与化学反应设置的误区,提供了实用的判断标准和修正方法,帮助工程师避免计算偏差,提升仿真精度。

weixin_29597551的博客 321

单例模式详解

一、什么是单例模式 单例模式是Java中最简单的设计模式之一。这种类型的设计模式属于创建者模式,它提供了一种访问对象的最佳方式。 这种设计模式涉及到一个单一的类,该类负责创建自己的对象,同时确保只有单个对象被创建。这个类提供了一种访问其唯一对象的方式,可以直接访问,不需要实例化该类的对象。 二、单例模式的结构 单例类:只能创建一个实例的类 访问类:使用单例类的类 三、单例模式分类 饿汉式:类加载就会导致该单实例对象被创建 懒汉式:类加载不会导致该单实例对象被创...

欢迎一起学习交流 2万+

tsmc12: m0po max length问题(H384.M0_PO.L.1)

手动调整可以挪cell,制造上下两个row相对的至少一个site的空间,通过插普通filler来解决,这里需要注意的是,tsmc12有via0的规则,需要让via0落在via0 grid上。在pt eco之后会有一些m0po max length问题出现,大部分问题都可以通过替换decap来解决,少部分由于局部density过高,需要手动调整。更多学习内容请关注「拾陆楼」知识星球。#ICC2中替换decap的参考脚本。

m0_61544122的博客 791

一文带你彻底搞懂设计模式之单例模式!!由浅入深,图文并茂,超超超详细的单例模式讲解!!

本篇文章通过图文形式,由浅入深,详细讲解了设计模式中的单例模式的应用

祝你身体健康,美满幸福 1万+

双馈风机并网系统宽频振荡机理与抑制方法研究

双馈风机并网系统宽频振荡分析与抑制 摘要:本文研究了双馈风机(DFIG)接入弱电网引发的宽频振荡问题。通过建立DFIG并网系统阻抗模型,分析了锁相环带宽、电流环带宽等参数对阻抗特性的影响。研究揭示了DFIG与电网阻抗交互导致交截频率处相位差超过180°的振荡机理。提出基于锁相环优化的阻抗重塑抑制策略,采用电压补偿和陷波器改善系统稳定性。仿真结果表明,该方法能有效降低相位差约10°-168°,显著抑制宽频振荡。代码实现了阻抗建模、稳定性分析和抑制策略验证,为工程应用提供了理论依据。

huanghm88的专栏 319

Nexys4DDR+OV7670实现图像灰度显示系统嵌入式

通过对硬件平台的准备、Vivado工程配置、OV7670驱动程序的编写、图像灰度处理算法的设计以及系统集成与测试,我们成功实现了一个基于嵌入式系统的图像处理应用。当系统运行时,OV7670摄像头模块将采集到的图像传输到FPGA芯片中,然后通过图像灰度处理算法将彩色图像转换为黑白图像,并在显示设备上进行显示。OV7670摄像头模块的驱动程序是实现图像采集的核心。以上代码中,我们使用了Xilinx提供的XGpio和Xil_In32函数来进行OV7670摄像头数据的读取和GPIO的初始化。OV7670驱动程序。

WangWEel的博客 338

细说单例模式

1.单例——东邪西毒南帝北丐 饥汉式(线程安全) public Class Singleton{ private static Singleton singleton = new Singleton(); private Singleton(){} public static Singleton getInstance(){ return singleton; } } 由于是类中的静态变量,当编...

花开蝶自来 115

Lammps不同亲疏水性粗糙表面的润湿行为模拟(包含in文件)

Lammps粗糙表面的润湿行为模拟(包含in文件)前言—润湿行为模拟一、物理模型构建二、具体in文件—in文件内循环亲疏水性三、具体in文件—分子模板构建初始模型以及平衡态模拟四、全部代码(基地粗糙表面只提供data文件) 前言—润湿行为模拟 润湿现象:当液体与固体接触时,液体的附着层将沿固体表面延伸。当接触角 θ\rm \thetaθ 为锐角时,液体润湿固体,若θ为零时,液体将展延到全部固体表面上。润湿现象的产生与液体和固体的性质有关。(来自百度百科) 润湿行为的本质是固液之间的相互作用,也就是分子间的范

Rockyoung 7093

细说单例模式中的双重检查锁

细说单例模式中的双重检查锁 - Decouple

Mrstonee的博客 321

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

细说设计模式之单例模式

一、单例模式思维导图 二、具体实现 1.饿汉式 public class Singleton1 { // 让构造方法私有,别人就没法创建此类的实例了 private Singleton1() { } //自己创建这个实例 private static final Singleton1 ME = new Singleton1(); //获取唯一...

lyf_0922的博客 227

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

细说Python设计模式之单例模式

@[T] 关于单例模式 单例模式提供了这样的一个机制,确保类有且只有一个特定类型的对象,并提供全局访问点。所以单例模式适用于以下情况:日志记录与数据库操作、打印机后台处理程序等等。因为这些程序运行过程中只能生成一个实例,用来避免对同一资源产生相互冲突的请求。 单例模式的特点: 确保有且只有一个对象被创建。 为对象提供一个访问点,以使程序可以全局访问该对象。 控制共享资源的并行访问。 S...

Apy 489

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

设计模式一 细说单例模式

通过设计模式思想的深入了解与运用,我们可以提高代码的可重用性,增强系统的可维护性,以及解决很多的复杂的问题。现实中我们不能准确的预测需求的变换,但是我们可以通过代码的设计来减少需求变换给我们带来的影响。在开发中我们无处不在的单一原则,迪米特原则,开闭原则等原则的适度使用是保证我们最终开发出来的代码健壮性的关键。 今天主要来说以下单例模式。 简介 单例模式就是单例对象的类只允许一个对象的存在,比如古...

qq_34517550的博客 302

腾讯一面:细说一下单例模式吧!

在Java语言中,我们知道有23种设计模式,这23种设计模式在Java语言涉及的框架源码中都有体现,比如在Spring框架中BeanFactory用到工厂模式,Spring的AOP切面结合Java的反射技术用到代理模式,Spring中的访问resource下的资源用到策略模式,Spring的bean默认是单例用到单例模式等等,那么接下来就重点为大家介绍下单例模式。饿汉式在类加载时已经创建好该对象,在程序调用时直接返回该单例对象即可,即我们在编码时就已经指明了要马上创建这个对象,不需要等到被调用时再去创建。

zjjcchina的博客 149

细说Java中的几种单例模式

2019独角兽企业重金招聘Python工程师标准>>> ...

weixin_33762130的博客 130

单例模式代码_MyBatis代码整洁之道模式设计模式细说单例模式

单例模式单例模式这里就不用情景模式讲解了,在平时开发中此模式还是用的比较多的。在WinForm开发的时候,一般设置程序都是使用的单例开发。定义:单例模式属于创建型模式,它用于保证一个类仅有一个实例,并提供一个访问它的全局访问点。要点:某个类只有有一个实例它必须自己创建这个实例他必须自行向整个系统提供这个实例和工具类的区别:在刚开始接触单例的时候,一直不明白为什么不直接都用static属性,这样明明...

weixin_39714164的博客 219

java中的单例_细说Java中的几种单例模式

在Java中,单例模式分为很多种,本人所了解的单例模式有以下几种,如有不全还请大家留言指点:饿汉式懒汉式/Double check(双重检索)静态内部类枚举单例一、饿汉式image饿汉式是在jvm加载这个单例类的时候,就会初始化这个类中的实例,在使用单例中的实例时直接拿来使用就好,因为加载这个类的时候就已经完成初始化,并且由于是已经加载好的单例实例因此是线程安全的,并发获取的情况下不会有问题,是一...

weixin_34583171的博客 263

细说DCL单例模式和volatile有什么关系,volatile在DCL中是必要的吗??

摘要: DCL(双重检查锁定)是Java实现线程安全单例的高效方式。标准代码通过两次if检查兼顾性能与安全:外层避免无谓锁竞争,内层防止重复创建。关键点在于volatile修饰实例变量,禁止new操作的指令重排序(1-3-2乱序),避免返回未初始化的"半成品对象"。其底层通过内存屏障和Happens-before规则(volatile写读顺序+传递性)确保线程安全。面试需强调:仅synchronized无法保证有序性,volatile解决了重排序引发的可见性问题。(149字)

weixin_46028606的博客 568

找对象需要单例模式吗?

一、情人节的故事     2015年8月20日情人节这天,我亲眼见了一场“疯狂的战斗”,里面的主人公是一位帅哥(这里暂且称小A),我走在去学校的路上,途径一个高档餐厅,当我矗立在餐厅窗户边的时候,看到里面有一对情侣在里面一起吃饭甚是浪漫,突然黑色的乌云笼罩了天空,我顺着乌云的方向透过明亮的窗户,看到了三个美女一起将那对情侣保卫了起来,这个时候小A想要溜走,此时却被三个美女一起抓住,只听里面说到:

一直在奋起,一直在路上 2527

细说单例设计模式

单例设计模式细说

weixin_41927555的博客 527

单例模式

简单介绍单例模式并用JAVA实现单例模式的经典方法,并会分析每种方法的优缺点,了解原理

平凡的博客 648

设计模式 - 单例模式

单例模式(Singleton),保证一个类仅有一个实例,并提供一个访问它的全局访问点。通常我们可以让一个全局变量使得一个对象被访问,但它不能防止你 实例化多个对象。一个最好的办法就是,让类自身负责保存它的唯一实例。这个类可以保证没有其他实例可以被创建,并且它可以提供一个访问该实例 的方法。单例模式的核心思想是将类的实例化过程控制在一个特定的范围内,以确保只有一个实例被创建并且全局可访问。这种模式在需要共享资源或避免重复创建相同对象的场景中非常有用。将类的构造函数设为私有,防止外部代码直接创建实例。

BASK2311的博客 548
上一篇: C++11新特性总结
下一篇: C++11文件目录操作简介
陈 祥
博客等级 码龄18年 9粉丝 8原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值