特殊类设计(5个)与类型转换

news2024/11/15 8:48:47

引子:在生活中我们经常有不同类的需求,因此我们有了特殊类的设计(有很多种模式等)。由于类型需求不同我们有了类型转换。今天我们就来略讲略讲一下这方面的知识。

特殊类设计(5个)

注意:关键字:explicit--防止隐式类型转换,final--该类不能被继承

一,设计一个类,不能被拷贝

思路:直接使用c++11新增知识delete,禁掉拷贝构造与赋值,或放到私有private中区,只声明不实现。

class objA
{
public:

	objA(const objA&) = delete;
	objA operator=(const objA&) = delete;
private:
	int _a;
};

二,设计一个类,只能在堆上创建对象

思路一:把初始构造放到私有区,在public区中流出相应的接口

class objA
{
public:
	static objA* Get_objA(int c=3)
	{
		return new objA(c);
	}

	objA(const objA&) = delete;
	objA operator=(const objA&) = delete;
private:
	objA(int a=1)
		:_a(a)
	{}
	int _a;
};

注意要禁掉拷贝构造或移动构造,否则仍能进行在其他区创建对象,如下

思路二:利用new的函数不自动调用析构函数来进行区分,同样是把析构函数弄成私有!(这里不实现了)

三,设计一个类,只能在栈上创建对象

思路:禁掉operator new(),在public,在单独写接口;

class objA final
{
public:
	static objA Get_objA(int c=3)
	{
		return objA(c);
	}

	objA(const objA&) = delete;
	objA operator=(const objA&) = delete;
	void* operator new(size_t size) = delete;
	void operator delete(void* p) = delete;
private:
	objA(int a=1)
		:_a(a)
	{}
	int _a;
};

int main()
{
	static objA h1;
	objA h2=objA::Get_objA(4);
	objA* h3 = objA::Get_objA();
	return 0;
}

四,设计一个类,不能被继承

思路:直接利用final进行控制

五,设计一个类,只能创建一个对象 

一,饿汉模式:不管你将来用不用,程序启动时就创建一个唯一的实例对象

缺点:

1、多个饿汉模式的单例,某个对象初始化内容较多(读文件),会导致程序启动慢

2、A和B两个饿汉,对象初始化存在依赖关系,要求A先初始化,B再初始化,饿汉无法保证

class objA final
{
public:
	static objA* Get_objA()
	{
		return &_cmp;
	}

	objA(const objA&) = delete;
	objA operator=(const objA&) = delete;
private:
	objA(int a=5)
		:_a(a)
	{}
	int _a;
	static objA _cmp;
};

objA* cmp=objA::Get_objA();
objA objA::_cmp;

二,懒汉模式:第一次使用实例对象时,创建对象。进程启动无负载。多个单例实例启动顺序自由控制

优点:如果单例对象构造十分耗时或者占用很多资源,比如加载插件啊, 初始化网络连接啊,读取 文件啊等等,而有可能该对象程序运行时不会用到,那么也要在程序一开始就进行初始化, 就会导致程序启动时非常的缓慢。 所以这种情况使用懒汉模式(延迟加载)更好。

class objA final
{
public:
	static objA& Get_objA()
	{
		if (_cmp == nullptr)
		{
			_cmp = new objA();
		}
	}

	static void destroy()
	{
		delete _cmp;
		_cmp = nullptr;
	}
	objA(const objA&) = delete;
	objA operator=(const objA&) = delete;
private:
	objA(int a=5)
		:_a(a)
	{}
	int _a;
	static objA* _cmp;
};

objA* objA::_cmp = nullptr;

int main()
{
	
	return 0;
}

类型转换

标准C++为了加强类型转换的可视性,引入了四种命名的强制类型转换操作符: static_cast、reinterpret_cast、const_cast、dynamic_cast

static_cast用于非多态类型的转换(静态转换),编译器隐式执行的任何类型转换都可用 static_cast,但它不能用于两个不相关的类型进行转换

// 对应隐式类型转换 -- 数据的意义没有改变
double d = 12.34;
int a = static_cast<int>(d);
cout << a << endl;

reinterpret_cast操作符通常为操作数的位模式提供较低层次的重新解释,用于将一种类型转换 为另一种不同的类型(强转)

// 对应强制类型转换 -- 数据的意义已经发生改变
int* p1 = reinterpret_cast<int*>(a);

const_cast最常用的用途就是删除变量的const属性,方便赋值

// 对应强制类型转换中有风险的去掉const属性
volatile const int b = 2;
int* p2 = const_cast<int*>(&b);
*p2 = 3;

dynamic_cast用于将一个父类对象的指针/引用转换为子类对象的指针或引用(动态转换),虽然,可以用隐私类型或强制类型进行转换,但是有越界风险!

向上转型:子类对象指针/引用->父类指针/引用(不需要转换,赋值兼容规则)

向下转型:父类对象指针/引用->子类指针/引用(用dynamic_cast转型是安全的)

注意:

1. dynamic_cast只能用于父类含有虚函数的类

2. dynamic_cast会先检查是否能转换成功,能成功则转换,不能则返回0

class A
{
public:
	virtual void f() {}
};
class B : public A
{};
void fun(A* pa)
{
	// dynamic_cast会先检查是否能转换成功,能成功则转换,不能则返回
	B* pb1 = static_cast<B*>(pa);
	B* pb2 = dynamic_cast<B*>(pa);
	cout << "pb1:" << pb1 << endl;
	cout << "pb2:" << pb2 << endl;
}
int main()
{
	A a;
	B b;
	fun(&a);
	fun(&b);
	return 0;
}

RTTI(字面上的意思):

RTTI:Run-time Type identification的简称,即:运行时类型识别。

C++通过以下方式来支持RTTI:

1. typeid运算符

2. dynamic_cast运算符

3. decltype

今天就到这里啦,我们大家一起加油!

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

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

相关文章

uniapp发布包app.json文件配置及发包上传注意事项

一、分包&#xff08;提示主包大小不小于1.5M&#xff09; 我的分包代码 二、未开启js压缩 操作:【必须】在工具「详情」-「本地设置」中开启「上传代码时自动压缩脚本文件」的设置 三、未开启组件懒注入&#xff08;按需注入&#xff09; 只需将代码"lazyCodeLoading&qu…

深度剖析:黑神化悟空的防御机制,为何成为破解难题?

深度剖析&#xff1a;黑神化悟空的防御机制&#xff0c;为何成为破解难题&#xff1f; 黑神话悟空还没发售就被破解&#xff1f; #国产游戏 #悟空 #西游记 推荐阅读&#xff1a; 全红婵抖音魅力无限&#xff0c;粉丝数量历史性突破1000万大关&#xff01; 奥运激情日&#…

【日记】今天实在太累了(436 字)

正文 今天的工作强度跟之前完全不是一个级别。能不能不要给我找这么多事做&#xff0c;我只想摸鱼摆烂。以后到下一个单位就说自己啥都不会好了&#xff0c;省得一天天全来找我。 忙碌程度上升了一个数量级&#xff0c;一天结束之后完全不想说话。 好想睡觉。 昨晚尝试完成年度…

利用ADB命令截屏,并发送至指定邮箱

需求分析: 为满足对Android设备远程监控、故障排查或自动化报告生成等应用场景需求,本指南将指导你如何利用ADB(Android Debug Bridge)工具实现Android设备的截屏功能,并介绍如何将截屏结果通过远程通知的形式发送至指定邮箱。 关键词:ADB、截屏、远程通知、发送邮箱 准备…

程序设计—气象数据共享平台设计与实现 项目源码30172

摘 要 当前&#xff0c;气象数据的及时获取和共享对于许多行业和个人具有重要意义。然而&#xff0c;存在着数据获取不便、共享不畅、数据可视化展示不足等问题。为了解决这些问题&#xff0c;本研究旨在设计和开发一个基于C语言的气象数据共享平台&#xff0c;结合React框架实…

天津国芯SP下载工具 加个防呆 避免选了OTA升级的固件(后缀带有SIG.BIN)

V2.1 20240828 天津国芯SP下载工具 加个防呆 避免选了OTA升级的固件&#xff08;后缀带有SIG.BIN&#xff09; 兆讯的芯片1902首次下载必须先下载key&#xff0c;再下载加密固件。 天津国芯没有这个限制&#xff0c;固件是明文的。 自测使用的版本信息&#xff1a; 本地最新…

count格式的数据转换(count to FPKM,count to TPM) 【GEO数据库】

在正式分析之前&#xff0c;对于数据的处理是至关重要的&#xff0c;这种重要性是体现在很多方面&#xff0c;其中有一点是要求分析者采用正确的数据类型。 对于芯片数据&#xff0c;原始数据进行log2处理之后可以进行很多常见的分析&#xff0c;比如差异分析、热图、箱线图、…

linux下一切皆文件,如何理解?

linux下一切皆文件&#xff0c;不管你有没有学过linux&#xff0c;都应该听过这句话&#xff0c;就像java的一切皆对象一样。 今天就来看看它的真面目。 你记住了&#xff0c;只要一个竞争退出它的PCB要被释放文件名&#xff0c;客服表也要被释放。那么&#xff0c;指向这个文件…

基于大数据的电信诈骗行为可视化系统含预测研究【lightGBM,XGBoost,随机森林】

文章目录 有需要本项目的代码或文档以及全部资源&#xff0c;或者部署调试可以私信博主项目介绍 电信诈骗预测与分析系统项目概述系统架构详细功能描述1. 数据预处理2. 数据可视化与分析3. 机器学习预测4. 系统集成与用户界面 技术亮点应用价值未来展望lightGBMXGBoost随机森林…

猫头虎分享:什么是信创体系?

猫头虎分享&#xff1a;什么是信创体系? 猫头虎技术团队&#xff1a;深入解析信创体系 引言&#xff1a;为什么信创体系是未来发展的关键&#xff1f; 大家好&#xff0c;我是猫头虎&#xff0c;今天我们来聊一聊科技领域的热议话题——信创体系。随着国内外信息技术产业的迅…

分布式云扩展 AI 边缘算力,助力用户智能化创新

近期&#xff0c;AI 创新圈再次发布重磅产品更新。OpenAI 全新旗舰版多模态模型 GPT-4o 横空出世&#xff0c;其打通文本、图像、视频的富媒体理解能力以及敏捷的智能化对话&#xff0c;将 AI 助手的人性化表达效果&#xff0c;提升至更高水平。 ​ 从技术源头来看&#xff0c…

栈OJ题——有效的括号

文章目录 一、题目链接二、解题思路三、解题代码 一、题目链接 有效的括号 题目描述&#xff1a;给定一个只包括 ‘(’&#xff0c;‘)’&#xff0c;‘{’&#xff0c;‘}’&#xff0c;‘[’&#xff0c;‘]’ 的字符串 s &#xff0c;判断字符串是否有效。括号匹配。 二、…

《大模型应用开发极简入门》学习成为善用 AI 的人!看完懂得90%的大模型!{含pdf版电子书}

&#x1f4d6;《大模型应用开发极简入门&#xff1a;基于GPT-4与ChatGPT》 真心建议学习大模型的朋友都去看看这本书&#xff0c;作为一本应用开发入门书&#xff0c;在豆瓣评分好评不断&#xff0c;其中知识点有不少值得深入研究的领域&#xff0c;适合小白初学者阅读学习的&…

【Google Maps JavaScript API】详解地图本地化(Localizing the Map)

文章目录 一、地图本地化概述1. 什么是地图本地化&#xff1f;2. 为什么需要地图本地化&#xff1f; 二、如何实现地图本地化&#xff1f;1. 准备工作2. 编写 HTML 文件3. 初始化地图 三、详细代码解析1. HTML 部分2. JavaScript 部分 四、如何在本地运行示例代码&#xff1f;五…

Spring Boot如何压缩Json并写入redis?

1.为什么需要压缩json&#xff1f; 由于业务需要&#xff0c;存入redis中的缓存数据过大&#xff0c;占用了10G的内存&#xff0c;内存作为重要资源&#xff0c;需要优化一下大对象缓存&#xff0c;采用gzip压缩存储&#xff0c;可以将 redis 的 kv 对大小缩小大约 7-8 倍&…

Jmeter录制脚本(不推荐,因为有大量冗余)

1、以百度举例 2、选择“Requests Filtering”&#xff0c;在“包含模式”中填入“.(baidu\.com).”用以过滤非http://baidu.com的请求&#xff1b; 同时在“排除模式”中填入“(?i).*\.(bmp|css|js|gif|ico|jpe?g|png|swf|woff|woff2|htm|html).”用以过滤js、图片、html等…

postman请求设置

postman请求设置 1、请求参数&#xff0c;只能是none、for-data、x-www...、raw等中的一个&#xff0c;不能多个。2、请求头类型3、案例4、测压 1、请求参数&#xff0c;只能是none、for-data、x-www…、raw等中的一个&#xff0c;不能多个。 2、请求头类型 根据请求头&#x…

用Python分析定性变量之间的相关性_对应分析模板

对应分析是一种多元统计分析方法&#xff0c;主要用于分析定性变量构成的列联表&#xff0c;揭示变量之间的关系。它通过将列联表中的数据转换为点的形式&#xff0c;在低维空间中表示出来&#xff0c;从而实现数据的可视化。这种方法特别适用于有多个类别的定性变量分析&#…

如何将开发工具设置成滚动鼠标改变字体大小

就在刚刚与温州那边技术开会&#xff0c;温州那边技术提出&#xff1a;字体太小&#xff0c;代码看不清&#xff0c;需要将字体放大。然后让我将IDE设置成按住键盘的Ctrl滚动鼠标&#xff0c;可以放大字体大小。。。顿时间的小小尴尬。下面我来记录一下究竟是怎么操作的&#x…

Excel 导入和导出--前后端整合

文章目录 Excel基础Easy Excel导出会员数据导入会员数据 前端代码:代码解析总结组件简介详细解释总结 用来操作excel文件的。银行网银系统导出交易明细数据、各种业务系统导出excel报表数据、批量导入业务数据。 Excel基础 **工作簿 workbook**就是一个文件工作表 sheet属于…