【C++数据结构】顶层父类的创建与类族结构的进化

news2024/11/23 16:34:14

文章目录

  • 前言
  • 一、为什么需要创建顶层父类
  • 二、创建顶层父类Object的意义
  • 三、创建顶层父类Object
    • 3.1 顶层父类接口
    • 3.2 Object具体实现
      • new和delete运算符重载的实现
      • == 和 != 的运算符重载实现
    • 3.3 纯虚析构函数实现
  • 四、类族的结构进化
    • 4.1 怎样进化
    • 4.2 SmartPointer的进化
    • 4.3 Exception类的进化
  • 总结


前言

在C++中,数据结构是编程的重要组成部分,用于组织和管理数据。为了更好地组织代码和实现代码重用,创建一个顶层父类在数据结构中具有重要意义。这个父类可以为不同数据结构提供通用的接口和行为,同时允许具体的数据结构类继承这些通用特性并添加自己特有的功能。本文将介绍如何在C++中创建这样的顶层父类,为不同数据结构的设计和实现提供了框架和结构。


一、为什么需要创建顶层父类

顶层父类的创建

  • 当代软件架构实践中的经验
  • 尽量使用单重继承的方式进行系统设计
  • 尽量保持系统中只存在单一的继承树

不幸的事实:

  • C++ 语言的灵活性使得代码中可以存在多个继承树
  • C++ 编译器的差异使得同样的代码可能表现不同的行为
    new 操作如果失败会发生什么 ?
    在不同的编译器和环境下都会有所差异。
    例如在vs的开发环境下,可以抛出一个exception
    在其他的开发环境下可能是空指针。
    那么这样就不可控,就大大降低我们的可移植性。

所以我们需要一个顶层父类来帮助我们

二、创建顶层父类Object的意义

创建 DbTLib: :0bject 类的意义

  • 遵循经典设计准则,所有数据结构都继承自 Object 类
  • 定义动态内存申请的行为,提高代码的移植性

三、创建顶层父类Object

3.1 顶层父类接口

class Object
{
public:
    /*throw()不会抛出异常*/
    void* operator new (size_t size) throw();
    void operator delete (void* p);
    void* operator new[](size_t size) throw();
    void operator delete[](void* p);
    bool operator == (const Object& obj);
    bool operator != (const Object& obj);
    virtual ~Object() = 0;
};

在这里插入图片描述

上面的代码定义了一个名为 Object 的C++类,其中包含了一些特殊的成员函数和声明。下面逐句解释这些代码:

1.class Object:
这一行定义了一个名为 Object 的C++类。这将是一个基类,其他类可以从它派生。
2.public::
这行指示以下成员函数和数据成员在类的公共部分,即可以在类的外部访问。
3.void* operator new (size_t size) throw(); :
这是一个重载的 new 运算符。它用于动态分配内存并返回一个指向该内存的指针。 size_t size 是要分配的内存块的大小。 throw() 关键字表示此运算符不会抛出异常。
4.void operator delete (void* p); :
这是一个重载的 delete 运算符。它用于释放通过 new 分配的内存。参数 void* p 是要释放的内存块的指针。
5.void* operator new[](size_t size) throw(); :
这是重载的数组 new 运算符,用于分配数组形式的内存块,并返回一个指向该内存的指针。 size_t size 指定要分配的内存块的总大小。同样,throw() 表示不会抛出异常。
6.void operator delete[](void* p); :
这是重载的数组 delete 运算符,用于释放通过数组 new 分配的内存。参数 void* p 是要释放的内存块的指针。
7.bool operator == (const Object& obj); :
这是一个自定义的相等运算符重载,用于比较两个 Object 类对象是否相等。
8.bool operator != (const Object& obj); :
这是一个自定义的不等运算符重载,用于比较两个 Object 类对象是否不相等。
9.virtual ~Object() = 0; :
这是 Object 类的虚析构函数。通过在其声明中使用 = 0,它被声明为纯虚函数。这意味着 Object 类是一个抽象基类,不能被实例化,只能用作其他类的基类。任何派生自 Object 的类都必须提供自己的析构函数实现。虚析构函数通常用于确保在派生类中的资源正确释放。

总的来说,这个 Object 类定义了一些特殊的成员函数,使其成为一个抽象基类,为其他类提供了通用的内存分配、释放、比较等功能。其他类可以继承自 Object 类,并实现其纯虚析构函数以添加自己的功能。这种设计通常用于创建一个对象层次结构,其中多个类共享一些通用行为。

3.2 Object具体实现

new和delete运算符重载的实现

我们需要想一下,如何申请空间才是可控的,不会抛出异常的。
当然是我们的malloc函数和free函数啦

所以在外面这个Object里面使用这两个函数来实现我们的运算符重载

void* Object::operator new (size_t size) throw()
{
    return malloc(size);
}

void Object::operator delete (void* p)
{
    free(p);
}

void* Object::operator new[](size_t size) throw()
{
    return malloc(size);
}

void Object::operator delete[](void* p)
{
    free(p);
}

在这里插入图片描述

== 和 != 的运算符重载实现

我们需要想一下,我们如何去对比本对象和其他对象是否相等呢,很显然,使用值相等是不可能的,因为我们这个Object没有提供任何的flag标识和标识我们这个类是谁

所以我们需要使用一种质朴的方法:比较内存地址,内存地址一样肯定是一样的东西,因为他们指向同一块空间。

bool Object::operator == (const Object& obj)
{
    return (this == &obj);
}

bool Object::operator != (const Object& obj)
{
    return (this != &obj);
}

在这里插入图片描述

3.3 纯虚析构函数实现

这里的析构并不需要实现具体功能,只需要写个函数体即可

Object::~Object()
{

}

四、类族的结构进化

4.1 怎样进化

我们需要写出一个单继承数,如下图:
在这里插入图片描述
我们下面的所有类都要继承Object父类,那么接下来我们就去实现他吧

4.2 SmartPointer的进化

我们直接进行继承即可,不需要改动

template<typename T>
class SmartPointer:public Object
{
protected:
	T* m_pointer;

public:
	SmartPointer(T* p = nullptr)
	{
		m_pointer = p;
	}

	//.........
};

在这里插入图片描述

4.3 Exception类的进化

和上面一样,我们也只需要进行简单的继承即可:

class Exception:public Object
{
protected:
    char* m_message;
    char* m_location;
    //.............
}

在这里插入图片描述

但是我想各位同学应该发现了一个问题,就是在我们的init函数中申请了空间,没有进行判断是否为空。
那么我们就去改吧:

char sl[16] = { 0 };

itoa(line, sl, 10);

m_location = static_cast<char*>(malloc(strlen(file) + strlen(sl) + 2));

if (m_location != NULL)
{
    m_location = strcpy(m_location, file);
    m_location = strcat(m_location, ":");
    m_location = strcat(m_location, sl);
}

在这里插入图片描述

那么else分支呢,是否需要throw抛出异常呢,其实是不需要的。我们只需要判断是否为空即可,然后进行对应的操作


总结

在C++中,创建顶层父类对于数据结构的设计和实现是非常有益的。它提供了通用的接口和行为,使得代码更易维护和扩展。通过继承和实现,具体的数据结构类可以在保持通用性的同时添加自己特有的功能。这种层次结构的设计有助于提高代码的可重用性和可读性,同时促进了良好的编程实践。希望本文能够帮助你更好地理解如何在C++中创建顶层父类以支持数据结构的设计。

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

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

相关文章

什么是Target Plus EDI?

“Target Plus” 是美国知名零售商Target&#xff08;塔吉特&#xff09;推出的一个合作伙伴计划。这个计划允许第三方卖家在Target.com&#xff08;塔吉特官方网站&#xff09;上销售他们的商品。通过Target Plus&#xff0c;第三方卖家可以将他们的产品列在Target.com上&…

uni-app 、Spring Boot 、ant Design 打造的一款跨平台包含小说(仿真翻页、段落听书)、短视频、壁纸等功能含完备后台管理的移动应用

简介 咪哩快看&#xff0c;为用户提供优质阅读&#xff0c;短视频&#xff0c;共同记录美好生活的移动应用&#xff0c;并含有一套完备的后台管理体系&#xff0c;助力开发者快速数字化&#xff0c;开启你的财富之门&#xff01; 官网&#xff1a; https://miliqkdoc.motopa.…

Antd Procomponent 之 proForm - 高级表单

本文作者系360奇舞团前端开发工程师 ProForm 在原来的 Form 基础上增加一些语法糖和更多的布局设置&#xff0c;帮助我们快速的开发一个表单。同时添加一些默认行为&#xff0c;让我们的表单默认好用。分步表单&#xff0c;Modal 表单&#xff0c;Drawer 表单&#xff0c;查询表…

DC电源模块的价格因素是什么?如何进行成本优化?

BOSHIDA DC电源模块的价格因素是什么&#xff1f;如何进行成本优化&#xff1f; DC电源模块是一种用于直流电路中的电源转换器&#xff0c;主要用于将输入电源的电压、电流和频率转换为适合设备的直流电源。随着电子设备的广泛应用&#xff0c;DC电源模块的需求也日益增加。而…

含泪整理的超全窗口函数:数据开发必备

最近在搞一些面试和课程答辩的时候&#xff0c;问什么是窗口函数&#xff0c;知道哪些窗口函数?最多的答案就是row_number、rank、dense_rank&#xff0c;在问一下还有其他的吗&#xff1f;这时同学就蒙了,还有其他的窗口函数&#xff1f;其实上面的回答也只是专用窗口函数&am…

多门店自助点餐+外卖二合一小程序源码系统 带完整搭建教程

随着餐饮业的快速发展和互联网技术的不断进步&#xff0c;越来越多的餐厅开始采用自助点餐和外卖服务。市场上许多的外卖小程序APP应运而生。下面罗峰来给大家介绍一款多门店自助点餐外卖二合一小程序源码系统。该系统结合了自助点餐和外卖服务的优势&#xff0c;为餐厅提供了一…

照明灯具哪个品牌好?照明灯具十大排行榜

现在儿童近视率越来越高了&#xff0c;用眼过度疲劳是导致近视的主要因素&#xff0c;学习环境的光线是否合适&#xff0c;都会直接影响用眼的疲劳程度。所以给孩子营造一个良好的学习环境非常重要&#xff01;一款护眼台灯可以很好的预防近视&#xff0c;为大家推荐五款护眼台…

【今日文章】:如何用css 实现星空效果

【今日文章】&#xff1a;如何用css 实现星空效果 需求实现tips: 需求 用CSS 实现星空效果的需求&#xff1a; 屏幕上有“星星”&#xff0c;且向上移动。移动的时候&#xff0c;动画效果要连贯&#xff0c;不能出现闪一下的样子。 实现 这里我们需要知道&#xff0c;“星星”是…

复杂逻辑的开发利器—Mendix快速实现AQL质量抽检

Mendix低代码开发平台适用于复杂的业务逻辑场景&#xff0c;这句话大家早有耳闻&#xff0c;本期小编就为您打开智慧之光&#xff0c;仅从AQL小侧面&#xff0c;来管窥一二——Mendix如何形成第五代编程语言&#xff0c;来完成数据逻辑与建模、业务算法逻辑与建模的。&#xff…

Excel下拉填充时,如何使得数字不递增?

问题描述&#xff1a;Excel下拉填充时&#xff0c;如何使得数字不递增&#xff1f; 解决办法&#xff1a;先下拉填充数据之后&#xff0c;看到最后一个单元格的右下角有个填充设置的符号&#xff0c;右键选择复制单元格即可。其中这里的填充序列就是递增数字的操作。

塔望食研院|骆驼奶市场规模庞大,百亿体量,品牌升级!

自2022年12月塔望咨询开设塔望食品大健康行业与消费研究院&#xff08;简称塔望食研院&#xff09;栏目以来&#xff0c;塔望食研院以“为食品行业品牌高质量发展赋能”为理念&#xff0c;不断发布食品大健康行业研究、消费研究报告。塔望食研院致力于结合消费调研数据、企业数…

如何使用ESB产品对接业务系统接口

ESB企业服务总线在实际项目中主要用于各业务系统之间的集成&#xff0c;集成包括数据集成、应用集成以及业务单据集成等&#xff0c;ESB企业服务总线主要包含三部分&#xff1a;ESB设计器、SMC管理控制台以及Server运行环境&#xff0c;ESB设计器用于服务以及集成流程的开发&am…

AI时代项目经理与架构师的成长之道:ChatGPT让你插上翅膀

&#x1f482; 个人网站:【工具大全】【游戏大全】【神级源码资源网】&#x1f91f; 前端学习课程&#xff1a;&#x1f449;【28个案例趣学前端】【400个JS面试题】&#x1f485; 寻找学习交流、摸鱼划水的小伙伴&#xff0c;请点击【摸鱼学习交流群】 在AI时代&#xff0c;项…

Ubuntu中增加交换内存

前言 在运行一些代码编译或者clang-format会占用大量的内存&#xff0c;此时可能会出现电脑卡死的情况&#xff0c;在ubuntu中可以通过增加交换内存来临时解决这个问题&#xff0c;相对于硬件改动成本更低&#xff0c;但是性能不如物理内存。 实践 查看当前的交换内存大小 …

【MySQL日志与备份篇】主从复制

主从复制 文章目录 主从复制1. 概述2. 主从复制的原理2.1 原理剖析2.2 复制的基本原则 3. 一主一从架构搭建3.1 准备工作3.2 主机配置文件3.3 从机配置文件3.4 主机&#xff1a;建立账户并授权3.5 从机&#xff1a;配置需要复制的主机3.6 停止主从同步3.7 后续 4. 同步数据一致…

关于WMS三个核心问题的解读

一、企业是否需要上WMS系统&#xff0c;可以从以下五个方面入手&#xff1a; 1.库存管理状况&#xff1a;了解企业的库存管理状况&#xff0c;是否存在库存冗余、漏洞、过度采购、库存盘点不准确等问题。 2.物流效率水平&#xff1a;需要了解企业物流效率水平&#xff0c;包括…

全网最全的设计模式专栏完结,建议点赞收藏

引言 代码写得烂可能并不是他的问题&#xff0c;推这个专栏给他看看。 本系列是《和8年游戏主程一起学习设计模式》&#xff0c;让糟糕的代码在潜移默化中升华。 大家好&#xff0c;白驹过隙&#xff0c;岁月如梭。本系列文章终于迎来了完结&#xff0c;距离开始已经一个多月…

阿里云Intel Xeon Platinum可扩展处理器性能如何?

阿里云Intel Xeon Platinum可扩展处理器性能如何&#xff1f;目前云服务器ECS经济型e实例采用该款CPU型号&#xff0c;正好阿里云服务器网购买了一台2核CPU、2G内存、3M固定带宽、40G ESSD Entry云盘&#xff0c;一年优惠价99元&#xff0c;第二年续费不涨价依旧是99元一年&…

nerdctl install【nerdctl 安装】

文章目录 1. 在线安装2. 离线安装 1. 在线安装 #!/bin/bashsource ./config.shENABLE_DOWNLOAD${ENABLE_DOWNLOAD:-true}if [ ! -e files ]; thenmkdir -p files fiFILES_DIR./files if $ENABLE_DOWNLOAD; thenFILES_DIR./tmp/filesmkdir -p $FILES_DIR fi# download files, i…

25期代码随想录算法训练营第十天 | 栈与队列 part 1

目录 232.用栈实现队列225. 用队列实现栈 232.用栈实现队列 链接 相当于用两个stack将队列的元素顺序颠倒了一遍。 class MyQueue:def __init__(self):self.stack_in []self.stack_out []def push(self, x: int) -> None:self.stack_in.append(x)def pop(self) -> in…