c++理解(三)

        本文主要探讨c++相关知识。

模板是对类型参数化
函数模板特化不是模板函数重载
allocator(空间配置器):内存开辟释放,对象构造析构
优先调用对象成员方法实现的运算符重载函数,其次全局作用域找
迭代器遍历访问元素,调用erase,insert方法后,当前位置到容器末尾元素的所有迭代器全部失效
malloc只开辟空间,new还可初始化
malloc开辟内存失败返回nullptr,new(malloc实现)抛出bad_alloc异常
delete(free实现)先调析构函数再free,无析构函数delete和free相同
new和delete也是函数重载符调用
除了对象的其他类型变量的数组和单个变量可混用delete/delete []
对象在new开辟内存时会多开辟4字节来存储对象个数,使用delete []时才可正确调用析构函数
对象池:短时间内多次使用用一块内存(new/delete)

demo1:

        vector实现

结构图:

 run.sh

#!/bin/bashif [ -f ./Makefile ]
thenmake clean
ficmake .makeecho "---------------------------------"./pro

CMakeLists.txt

CMAKE_MINIMUM_REQUIRED(VERSION 3.28)                            #最低版本要求SET(CMAKE_CXX_COMPILER "g++-11")                                #设置g++编译器PROJECT(CLASS)                                                  #设置工程名MESSAGE(STATUS "CPP test")                                      #打印消息ADD_EXECUTABLE(pro test.cpp)                                    #生成可执行文件

clean.sh

rm -rf CMakeCache.txt CMakeFiles Makefile cmake_install.cmake *.o pro

test.cpp

#include <iostream>//空间配置器
template<typename T>
struct Allocator
{//开辟空间T* Allocate(size_t size){return (T*)malloc(sizeof(T) * size);}//释放空间void des_Allocate(void *p){free(p);}//构造元素void construct(T *p,const T& value){new (p) T(value);}//释放元素void des_construct(T *p){p->~T();}
};template<typename T,typename Alloc = Allocator<T>>
class vector
{public:vector(int size = 5){first = allocator.Allocate(size);last = first;end = first + size;}~vector(){for(T *p = first; p != last; p++){allocator.des_construct(p);}allocator.des_Allocate(first);first = last = end = nullptr;}vector(const vector<T> &rhs){first = allocator.Allocate(rhs.end - rhs.first);last = first + (rhs.last - rhs.first );end = first + (rhs.end - rhs.first);for(T *p = first; p != last; p++){allocator.construct(p,*(rhs.first + (p - first)));}}vector &operator=(const vector<T> &rhs){if(this == &rhs)return *this;delete [] first;first = allocator.Allocate(rhs.end - rhs.first);last = first + (rhs.last - rhs.first );end = first + (rhs.end - rhs.first);for(T *p = first; p != last -1; p++){allocator.construct(p,*(rhs.first + (p - first)));}}void push_back(const T& value){if(full())expand();allocator.construct(last,value);last++;}void pop_back(){if(empty())return;allocator.des_construct(last);last--;}T front() const{return *first;}T back() const{return *(last - 1);}bool full() const {return last  == end;}bool empty() const{return first == last;}T* data() const{return first;}size_t size() const{return (last - first);}T &operator[](unsigned int index) const{if(index > size())throw "out of range";return first[index];}T &at(unsigned int index){if(index > size())throw "out of range";return first[index];}size_t capacity() const{return (end - first);}//迭代器class iterator{public:friend class vector<T,Alloc>;iterator(vector<T,Alloc> *pvec = nullptr,T *ptr = nullptr):pvec(pvec),ptr(ptr){Iterator_Base *itb = new Iterator_Base(this,pvec->head.next);pvec->head.next = itb;};T &operator*() const{if(pvec == nullptr)throw "iterator invaild";return *ptr;}T *operator->() const{if(pvec == nullptr)throw "iterator invaild";return ptr;}T *operator++() {if(pvec == nullptr)throw "iterator invaild"; return ++ptr;}T *operator++(int) {if(pvec == nullptr)throw "iterator invaild";return ptr++;}T *operator--(){if(pvec == nullptr)throw "iterator invaild";return --ptr;}T *operator--(int){if(pvec == nullptr)throw "iterator invaild";return ptr--;}bool operator==(const iterator &it){//迭代器为空,两个不同迭代器if(pvec == nullptr || pvec != it.pvec)throw "iterator incompatable";return ptr == it.ptr;}bool operator!=(const iterator &it) const{//迭代器为空,两个不同迭代器if(pvec == nullptr || pvec != it.pvec)throw "iterator incompatable";return ptr != it.ptr;}private:T* ptr;vector<T,Alloc> *pvec;};//头迭代器iterator ibegin(){return iterator(this,first);}//尾迭代器iterator iend(){return iterator(this,last);}//迭代器失效,释放元素资源void iterator_clear(T *first,T *last){Iterator_Base *pre = &(this->head);Iterator_Base *it = this->head.next;while(it != nullptr){if(it->cur->ptr > first && it->cur->ptr <= last){it->cur->pvec = nullptr;pre->next = it->next;delete it;it = pre->next;}else{pre = it;it = it ->next;}}}//元素插入方法,迭代器失效iterator insert(iterator it, const T &val){iterator_clear(it.ptr - 1,last);T *p = last;while (p > it.ptr){allocator.construct(p, *(p-1));allocator.des_construct(p - 1);p--;}allocator.construct(p, val);last++;return iterator(this, p);}//元素擦除方法,迭代器失效iterator erase(iterator it){iterator_clear(it.ptr - 1,last);T *p = it.ptr;while (p < last-1){allocator.des_construct(p);allocator.construct(p, *(p+1));p++;}allocator.des_construct(p);last--;return iterator(this, it.ptr);}private:T *first;T *last;T *end;Alloc allocator;//迭代器指针,迭代器失效释放资源和重构迭代器struct Iterator_Base{Iterator_Base(iterator *c = nullptr,Iterator_Base *next = nullptr):cur(c),next(next){};iterator *cur;Iterator_Base *next;};Iterator_Base head;//扩容方法void expand(){int size = end - first;T* tmp = allocator.Allocate(2 * size);for(int i = 0;i < size;i++){allocator.construct(tmp + i,*(first + i));allocator.des_construct(first + i);}allocator.des_Allocate(first);first = tmp;last = tmp + size;end = tmp + (2 * size);}};class Test
{public:Test(){};Test(int num):num(num){};int num;
};int main()
{Test t1(1),t2(2),t3(3),t4(4),t5(5),t6(6);vector<Test> v;v.push_back(t1);v.push_back(t2);v.push_back(t3);v.push_back(t4);v.push_back(t5);v.push_back(t6);vector<Test> v1(v);vector<Test> v2 = v1;vector<Test> v3 = v1;std::cout << "front():" << v2.front().num << std::endl;std::cout << "back():" << v2.back().num << std::endl;std::cout << "data():" << v2.data()->num << std::endl;std::cout << "size():" << v2.size() << std::endl;std::cout << "[]:" << v2[1].num << std::endl;std::cout << "at():" << v2.at(1).num << std::endl;std::cout << "capacity():" << v2.capacity() << std::endl;v2.pop_back();v2.pop_back();v2.pop_back();v2.pop_back();v2.pop_back();v2.pop_back();std::cout << "v:";for(auto it = v.ibegin();it != v.iend();it++){std::cout << it->num << " ";}std::cout << std::endl;for(auto it = v.ibegin();it != v.iend();it++){if(it->num == 2){it = v.insert(it,7);++it;}}std::cout << "v:";for(auto it = v.ibegin();it != v.iend();it++){std::cout << it->num << " ";}std::cout << std::endl;std::cout << "v1:";for(auto it = v1.ibegin();it != v1.iend();++it){std::cout << it->num << " ";}std::cout << std::endl;for(auto it = v1.ibegin();it != v1.iend();++it){if(it->num == 4){it = v1.erase(it);++it;}}std::cout << "v1:";for(auto it = v1.ibegin();it != v1.iend();++it){std::cout << it->num << " ";}std::cout << std::endl;std::cout << "v2:";for(auto it = v2.ibegin();it != v2.iend();it++){std::cout << it->num << " ";}std::cout << std::endl;auto it_v3_end = v3.iend();std::cout << "*(it_v3_end--):" << (it_v3_end--)->num << std::endl;std::cout << "*(--it_v3_end):" << (--it_v3_end)->num << std::endl;return 0;
}

结果示例:

demo2:

        对象池

结构图:

 run.sh

#!/bin/bashif [ -f ./Makefile ]
thenmake clean
ficmake .makeecho "---------------------------------"./pro

CMakeLists.txt

CMAKE_MINIMUM_REQUIRED(VERSION 3.28)                            #最低版本要求SET(CMAKE_CXX_COMPILER "g++-11")                                #设置g++编译器PROJECT(CLASS)                                                  #设置工程名MESSAGE(STATUS "CPP test")                                      #打印消息ADD_EXECUTABLE(pro test.cpp)                                    #生成可执行文件

clean.sh

rm -rf CMakeCache.txt CMakeFiles Makefile cmake_install.cmake *.o pro

test.cpp

#include <iostream>
#include <time.h>template<typename T>
class Queue
{public:Queue(){front = rear = new QueueItem(); }~Queue(){QueueItem *tmp = front;while(tmp != nullptr){front = front->next;delete tmp;tmp = front;}}void push(const T& val){QueueItem *tmp = new QueueItem(val);rear->next = tmp;rear = tmp;}void pop(){if(empty())return;QueueItem* tmp = front->next;front->next = tmp->next;if (front->next == nullptr){rear = front;}delete tmp;}bool empty(){return front == rear;}private:struct QueueItem{QueueItem(T data = T()):data(data),next(nullptr){};static void * operator new(size_t size){if(itempool == nullptr ){itempool = (QueueItem*)new char[sizeof(QueueItem) * POOL_SIZE];QueueItem *tmp = itempool;for(;tmp < itempool + POOL_SIZE - 1;tmp++){tmp->next = tmp + 1;}              tmp->next = nullptr;}QueueItem *tmp = itempool;itempool = itempool->next;return tmp;}static void operator delete(void *p){QueueItem* tmp = (QueueItem*)p; tmp->next = itempool;itempool = tmp;}T data;QueueItem *next;static QueueItem* itempool;static const unsigned int POOL_SIZE = 1000000;};static int num;QueueItem *front;QueueItem *rear;
};template<typename T> 
typename Queue<T>::QueueItem* Queue<T>::QueueItem::itempool = nullptr;class Test
{public:Test(){};Test(int n){};~Test(){};private:
};int main()
{Queue<Test> t;for(int i = 0;i < 1000000;i++){t.push(Test(i));t.pop();}std::cout << "run time: " <<(double)clock() / CLOCKS_PER_SEC << "s" << std::endl;return 0;
}

结果示例:

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

实训项目11基于51单片机的门禁监测系统设计

00 要求 基于51单片机和RFID模块实现门禁的设计。使之具有以下功能: 能够正常的读卡信息&#xff1b;在正常刷卡通过后&#xff0c;可以控制电子锁动作&#xff1b;在刷卡失败后&#xff0c;可以产生报警信号; 01 功能分析 读卡后会RFID会自动通过TXD&#xff08;串口&…

opencv——识别图片颜色并绘制轮廓

图像边缘检测 本实验要用到Canny算法&#xff0c;Canny边缘检测方法常被誉为边缘检测的最优方法。 首先&#xff0c;Canny算法的输入端应为图像的二值化结果&#xff0c;接收到二值化图像后&#xff0c;需要按照如下步骤进行&#xff1a; 高斯滤波。计算图像的梯度和方向。非极…

源码安装PHP-7.2.19

源码安装PHP-7.2.19 1.解压 tar -xjvf php-7.2.19.tar.bz2.编译 -prefix安装路径 cd php-7.2.19 ./configure --prefix/home/work/study 成功输出 3.make(构建) makemake testmake installlinux对php操作的一些命令 # 进入到php [rootvdb1 study]# cd php/ [rootvdb1 st…

数据库管理-第271期 Oracle 23ai:用MongoDB的方式来操作JSON二元性(20241214)

数据库管理271期 2024-12-14 数据库管理-第271期 Oracle 23ai&#xff1a;用MongoDB的方式来操作JSON二元性&#xff08;20241214&#xff09;1 初始化数据1.1 创建用户1.2 导入数据1.3 创建JSON关系二元性视图 2 创建ORDS服务2.1 下载JDK172.2 安装ORDS2.3 启用MongoDB API2.4…

2024 年的科技趋势

2024 年在科技领域有着诸多重大进展与突破。从人工智能、量子计算到基因组医学、可再生能源以及新兴技术重塑了众多行业。随着元宇宙等趋势的兴起以及太空探索取得的进步&#xff0c;未来在接下来的岁月里有望继续取得进展与突破。让我们来探讨一下定义 2024 年的一些关键趋势&…

WPF+MVVM案例实战与特效(三十八)- 封装一个自定义的数字滚动显示控件

文章目录 1、运行效果2、案例实现1、功能设计2、页面布局3、控件使用4、运行效果3、拓展:多数字自定义控件1、控件应用4、总结1、运行效果 在Windows Presentation Foundation (WPF)应用程序中,自定义控件允许开发者创建具有特定功能和外观的独特UI元素。本博客将介绍一个名…

ElasticSearch的自动补全功能(拼音分词器、自定义分词器、DSL实现自动补全查询、RestAPI实现自动补全查询)

文章目录 1. 什么是自动补全2. 拼音分词器2.1 初识拼音分词器2.2 下载拼音分词器2.3 安装拼音分词器2.4 测试拼音分词器 3. 自定义分词器3.1 拼音分词器存在的问题3.2 分词器&#xff08;analyzer&#xff09;的组成3.3 如何自定义分词器3.4 拼音分词器的可选参数3.5 配置自定义…

八股—Java基础(二)

目录 一. 面向对象 1. 面向对象和面向过程的区别&#xff1f; 2. 面向对象三大特性 3. Java语言是如何实现多态的&#xff1f; 4. 重载&#xff08;Overload&#xff09;和重写&#xff08;Override&#xff09;的区别是什么&#xff1f; 5. 重载的方法能否根据返回值类…

Java-08

类的抽象是将类的实现和使用分离, 而类的封装是将实现的细节封装起来并且对用户隐藏,用户只需会用就行。 类的合约指的是从类外可以访问的方法和数据域的集合以及与其这些成员如何行为的描述 isAlive()方法的返回值类型为布尔型&#xff08;Boolean&#xff09;。这个方法用于…

【MATLAB第109期】基于MATLAB的带置信区间的RSA区域敏感性分析方法,无目标函数

【MATLAB第108期】基于MATLAB的带置信区间的RSA区域敏感性分析方法&#xff0c;无目标函数 参考第64期文章【MATLAB第64期】【保姆级教程】基于MATLAB的SOBOL全局敏感性分析模型运用&#xff08;含无目标函数&#xff0c;考虑代理模型&#xff09; 创新点&#xff1a; 1、采…

机器视觉与OpenCV--01篇

计算机眼中的图像 像素 像素是图像的基本单位&#xff0c;每个像素存储着图像的颜色、亮度或者其他特征&#xff0c;一张图片就是由若干个像素组成的。 RGB 在计算机中&#xff0c;RGB三种颜色被称为RGB三通道&#xff0c;且每个通道的取值都是0到255之间。 计算机中图像的…

[数据结构#2] 图(1) | 概念 | 邻接矩阵 | 邻接表 | 模拟

图是由顶点集合及顶点间的关系&#xff08;边&#xff09;组成的数据结构&#xff0c;可用 G ( V , E ) G(V,E) G(V,E)表示&#xff0c;其中&#xff1a; 顶点集合 V V V: V { x ∣ x ∈ 某数据对象集 } V\{x|x\in\text{某数据对象集}\} V{x∣x∈某数据对象集}&#xff0c;…

自动驾驶---小米汽车智驾进展

1 背景 小米汽车的进度&#xff0c;可能出乎很多人的意料&#xff0c;其它新势力车企花了5---10年的时间&#xff0c;小米汽车三年就成功造出了第一辆车&#xff0c;在小米su7月销2万的同时&#xff0c;获得了非常不错的口碑。笔者在之前的博客《微自传系列---雷军》中已经阐述…

IOTIQS100芯片, TCP 发送数据+NSOSD,data要是hex16进制转换方法

命令&#xff1a;data以十六进制字符串格式发送的数据。 方法 代码 sprintf(temp, "%02X", data[i]);&#xff1a;将当前字节转换为两位宽的大写十六进制字符&#xff0c;并存储在 temp 中。如果需要小写字母&#xff0c;可以将格式说明符改为 "%02x"。 …

3.metagpt中的软件公司智能体 (Architect 角色)

目录 基础流程1. WriteDesign 动作类2. Architect 角色类3. 流程说明&#xff1a;4. Mermaid图&#xff1a;总结&#xff1a; 代码1. WriteDesign类2. Architect角色3. 上下文&#xff0c;即数据结构4. 数据准备4. 初次编写5. 重写 基础流程 用于管理软件开发任务的系统的一部…

虚幻引擎NPR角色渲染

VRM4U导入 VRM4U插件 安装插件后需在项目设置勾选settings&#xff0c;就可以把VRM格式导入拖拽进UE 专业模型创作分享社区_模之屋_PlayBox 重定向 导入的骨骼和小白人Mannequin的骨骼会显示incompatible,需要用IK_Mannequin跟小白人的IK_Mannequin做retarget。 这边注意如果…

LabVIEW汽车综合参数测量

系统基于LabVIEW虚拟仪器技术&#xff0c;专为汽车带轮生产中的质量控制而设计&#xff0c;自动化测量和检测带轮的关键参数。系统采用PCIe-6320数据采集卡与精密传感器结合&#xff0c;能够对带轮的直径、厚度等多个参数进行高精度测量&#xff0c;并通过比较测量法判定产品合…

基于matlab的单目相机标定

链接&#xff1a; 单目相机标定&#xff08;使用Matlab&#xff09; 用Matlab对单目相机参数的标定步骤&#xff08;保姆级教程&#xff09; 1.准备代码 调用摄像头代码&#xff08;用于测试摄像头是否可用&#xff09;&#xff1a; #https://blog.csdn.net/qq_37759113/art…

景联文科技入选中国信通院发布的“人工智能数据标注产业图谱”

近日&#xff0c;由中国信息通信研究院、中国人工智能产业发展联盟牵头&#xff0c;联合中国电信集团、沈阳市数据局、保定高新区等70多家单位编制完成并发布《人工智能数据标注产业图谱》。景联文科技作为人工智能产业关键环节的代表企业&#xff0c;入选图谱中技术服务板块。…

实景视频与模型叠加融合?

[视频GIS系列]无人机视频与与实景模型进行实时融合_无人机视频融合-CSDN博客文章浏览阅读1.5k次&#xff0c;点赞28次&#xff0c;收藏14次。将无人机视频与实景模型进行实时融合是一个涉及多个技术领域的复杂过程&#xff0c;主要包括无人机视频采集、实景模型构建、视频与模型…