list的模拟实现(一)

在这里插入图片描述

嗨喽大家好,时隔许久阿鑫又给大家带来了新的博客,list的模拟实现(一),下面让我们开始今天的学习吧!

list的模拟实现(一)

1.list splice接口的使用

2.list尾插的实现

3.list的迭代器模拟实现

4.const迭代器

5.insert和erase的模拟实现

1.list splice接口的使用

在这里插入图片描述

int main()
{std::list<int> mylist1;mylist1.push_back(1);mylist1.push_back(2);mylist1.push_back(3);mylist1.push_back(4);auto it = find(mylist1.begin(), mylist1.end(), 3);mylist1.splice(++mylist1.begin(), mylist1, it);//1324for (auto ch: mylist1){cout << ch << " ";}cout << endl;return 0;
}

在这里插入图片描述

2.list尾插的实现

在这里插入图片描述

3.list的迭代器模拟实现

原生指针的++是连续的物理空间的++。
因为类能进行运算符重载,我直接对节点进行++达不到我的要求,所以我就将节点指针封装成一个类,这个类的行为就是遍历双向循环列表
每一个类都有自己需要完成的事情,也可以是几个类互相搭配完成一件事情。

在这里插入图片描述

template<class T>struct ListNode{ListNode<T>* _next;ListNode<T>* _prev;T _date;ListNode(const T& date = T()):_next(nullptr),_prev(nullptr),_date(date){}};template<class T>class ListIterator{typedef ListNode<T> Node;//此处传T的时候就相当于实例化typedef ListIterator<T> self;public:ListIterator(Node* node)//用一个节点的指针来构造:_node(node){}//++itself& operator++()
{_node = _node->_next;return *this;
}self operator++(int)//后置
{self tmp(*this);_node = _node->_next;return tmp;
}self& operator--()
{_node = _node->_prev;return *this;
}self operator--(int)//后置
{self tmp(*this);_node = _node->_prev;return tmp;
}T& operator*()
{return _node->_date;
}T* operator->()
{return &_node->_date;
}bool operator!=(const self& it)
{return _node != it._node;
}
bool operator==(const self& it)
{return _node == it._node;
}private://成员是一个节点的指针,将指针封装成类来达到我们想要实现的操作Node* _node;};template<class T>class list{public:typedef ListNode<T> Node;typedef ListIterator<T> iterator;//若T为int相当于实例化了一个int类型的iteratoriterator begin(){return iterator(_head->_next);}iterator end(){return iterator(_head);}list(){_head = new Node();_head->_next = _head;_head->_prev = _head;}void push_back(const T& x){Node* newnode = new Node(x);Node* tail = _head->_prev;//head  2  3   tail  newnodetail->_next = newnode;newnode->_prev = tail;newnode->_next = _head;_head->_prev = newnode;}private:Node* _head;};

iterator类不需要写析构函数,构造函数。节点是由链表管理的。(一般一个类不写析构函数,就不用写拷贝构造和赋值

在C、C++等语言中,指针访问结构体(struct)或联合体(union)的成员时,我们使用箭头(->)操作符。而当我们**直接访问结构体或联合体的成员(即不通过指针)时,我们使用点(.)**操作符。

注意:对于->操作符,可以得到一个指向节点有效数据的指针(下图pos坐标(中存储的是行和列)类似于节点中的_date),应该如下图注释所进行调用,但是编译器为了可读性,强行省略了一个箭头

在这里插入图片描述

struct pos
{int _row;int _col;pos(int row = 0,int col = 0 ):_row(row),_col(col){}};void list_test2()
{list<pos> it1;it1.push_back(pos(100,200));it1.push_back(pos(200,300));it1.push_back(pos(300,400));list<pos>::iterator it = ++it1.begin();while (it != it1.end()){cout << it->_col << ":" << it->_row <<endl;it++;}cout << endl;
}

匿名对象的临时对象可以调用非const的成员函数

4.const迭代器

const迭代器不能是普通迭代器前加const
const迭代器目标本身可以修改,指向的内容不能修改,类似const T* p

注意:不能在模板参数T前加上const

在这里插入图片描述

第一种方式:

template<class T>
class ListConstIterator
{typedef ListNode<T> Node;//此处传T的时候就相当于实例化typedef ListConstIterator<T> self;
public:ListConstIterator(Node* node)//用一个节点的指针来构造:_node(node){}//++itself& operator++(){_node = _node->_next;return *this;}self operator++(int)//后置{self tmp(*this);_node = _node->_next;return tmp;}self& operator--(){_node = _node->_prev;return *this;}self operator--(int)//后置{self tmp(*this);_node = _node->_prev;return tmp;}const T& operator*(){return _node->_date;}const T* operator->(){return &_node->_date;}bool operator!=(const self& it){return _node != it._node;}bool operator==(const self& it){return _node == it._node;}private://成员是一个节点的指针,将指针封装成类来达到我们想要实现的操作Node* _node;
};template<class T>
class list
{public:typedef ListNode<T> Node;typedef ListIterator<T> iterator;//若T为int相当于实例化了一个int类型的iteratortypedef ListConstIterator<T> const_iterator;iterator begin(){return iterator(_head->_next);}iterator end(){return iterator(_head);}const_iterator begin()const{return iterator(_head->_next);}const_iterator end()const{return iterator(_head);}

在这里插入图片描述

第二种方式:不同的模板参数表达的是不同的类,正如vector< int>和vector< double>表达的是两个不同的类

template<class T,class Ref,class Ptr>
class ListIterator
{typedef ListNode<T> Node;//此处传T的时候就相当于实例化typedef ListIterator<T,Ref,Ptr> self;
public:ListIterator(Node* node)//用一个节点的指针来构造:_node(node){}//++itself& operator++(){_node = _node->_next;return *this;}self operator++(int)//后置{self tmp(*this);_node = _node->_next;return tmp;}self& operator--(){_node = _node->_prev;return *this;}self operator--(int)//后置{self tmp(*this);_node = _node->_prev;return tmp;}Ref operator*(){return _node->_date;}Ptr operator->(){return &_node->_date;}bool operator!=(const self& it){return _node != it._node;}bool operator==(const self& it){return _node == it._node;}private://成员是一个节点的指针,将指针封装成类来达到我们想要实现的操作Node* _node;
};

5.insert和erase的模拟实现

链表的insert没有迭代器失效,erase迭代器有失效

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

好啦,今天的内容我们就学习到这里,如果大家觉得阿鑫写的不错的话,记得留下你的一键三连哦,期待我们的下一次相遇!

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

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

相关文章

Python编程的黑暗魔法:模块与包的神秘力量!

哈喽&#xff0c;我是阿佑&#xff0c;今天给大家讲讲模块与包~ 文章目录 1. 引言1.1 模块化编程的意义1.2 Python中模块与包的概念概述 2. 背景介绍2.1 Python模块系统模块的定义与作用Python标准库简介 2.2 包的结构与目的包的定义与目录结构包在项目组织中的重要性 3. 创建与…

【C语言】strstr函数的使用和模拟

前言 今天给大家带来一个字符串函数&#xff0c;strstr()的使用介绍和模拟实现。 模拟实现这个函数&#xff0c;可以帮助我们更深刻地理解这个函数的功能和提高解决字符串相关问题的能力&#xff0c;有兴趣的话就请往下看吧。 strstr函数介绍 函数功能&#xff1a; strstr函…

Three.js 研究:3、创建一个高科技圆环

打开Alpha混合 修改环形颜色&#xff0c;更改发光的颜色&#xff0c;更改发光的强度为2 更改世界环境灯光

如何编辑 PDF 中的文本?4个有效的编辑PDF方法

PDF 文件可以轻松打开和查看&#xff0c;但修改要复杂得多 - 尤其是在 PDF 中的文本编辑方面。 知道如何离线编辑 PDF 中的文本对于任何需要快速更改而无需在线加载文档或担心安全问题的人来说都非常有益。它使用户能够更好地控制他们的文档&#xff0c;并有更广泛的字体和图形…

着急联系媒体投稿发表文章有什么好方法?

作为一名曾经的信息宣传员,我深知在紧张的宣传节点上,急于将精心撰写的文章推向更广阔的读者群体,那种紧迫感和焦虑几乎成了常态。记得那段时间,为了能让稿件得到及时有效的曝光,我不得不亲自踏上了一场寻找媒体联系方式的“马拉松”。那时,我手头的资源有限,仅有的几个联系方式…

JRT1.7发布

JRT1.7连仪器在线演示视频 JRT1.5实现质控主体、1.6基本完成质控&#xff1b;本次版本推进到1.7&#xff0c;1.7集菜单权限、登录、打印导出客户端、初始化、质控、Linux客户端、仪器连接和监控体系各种功能大全&#xff0c;上十年写系统用到的都全了。 这次直接挑战检验最难…

就业信息|基于SprinBoot+vue的就业信息管理系统(源码+数据库+文档)

就业信息管理系统 目录 基于SprinBootvue的就业信息管理系统 一、前言 二、系统设计 三、系统功能设计 1前台功能模块 2后台功能模块 4.2.1管理员功能 4.2.2学生功能 4.2.3企业功能 4.2.4导师功能 四、数据库设计 五、核心代码 六、论文参考 七、最新计算机毕设…

MySql基础(一)--最详细基础入门,看完就懂啦(辛苦整理,想要宝宝的赞和关注嘻嘻)

前言 希望你向太阳一样&#xff0c;有起有落&#xff0c;不失光彩~ 一、数据库概述 1. 什么是数据库 数据库就是存储数据的仓库&#xff0c;其本质是一个文件系统&#xff0c;数据按照特定的格式将数据存储起来&#xff0c;用户可以对数据库中的数据进行增加&#xff0c;修改&…

大白话DC3算法

DC3算法是什么 DC3算法&#xff08;也称为Skew算法&#xff09;是一种高效的构建后缀数组的算法&#xff0c;全称为Difference Cover Modulo 3算法。 该算法于2002年被提出&#xff0c;论文参考&#xff1a; https://www.cs.cmu.edu/~guyb/paralg/papers/KarkkainenSanders0…

Vue3:封装Table 表格组件

组件官网 elementPlus : 点击跳转 封装组件 创建新的组件文件: Table.vue <!-- PropTableS &#xff1a; 父组件传递过来的数据 (对象)PropTableS.tables : 父组件传递的对象中 存放表格每行显示的数据PropTableS.keyS &#xff1a; 父组件传递过来的对象&#xff0c;里…

docker搭建私有仓库并推送本地镜像

1、私仓搭建 docker pull registry#拉取镜像 docker images#查看镜像 mkdir -p /czx/myregistry 创建挂载目录 运行私有库registry (相当于本地有个是有docker hub) docker run -d -p 5000:5000 -v /czx/myregistry/:/tmp/registry --restartalways --privilegedtrue regist…

STM32 USART的字符编码(发送器的实现逻辑)

目录 概述 1 字符编码 1.1 USART 字符说明 1.2 字长编程 2 发送器 2.1 字符发送 2.2 可配置的停止位 2.3 配置停止位方法 3 单字节通信 4 中断字符 5 空闲字符 概述 本文主要讲述STM32 USART的发送端功能实现的原理&#xff0c;包括字节编码长度&#xff0c;发送器…

MOS选型及其参数解析

背景&#xff1a; 整理现有常用元器件选型&#xff0c;日后使用时针对性观看&#xff0c;生成列表链接如下&#xff1a; https://blog.csdn.net/caozhaokun/article/details/126069701 作者&#xff1a;Cayden 时间&#xff1a;2024/05/26 一、MOS选用现状 MOS是电路设计…

【JavaEE初阶】HTTP协议|HTTP请求|URL基本格式|URLencode

&#x1f4a1;推荐 前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。【点击跳转到网站】 HTTP请求(Request) 认识URL URL基本格式 平时我们俗称的"⽹址"其实就是说的URL(Uniform Resource Loc…

MySQL--备份恢复

目录 一、备份恢复的工作职责 1.备份的时间周期 2.备份的方式 3.恢复方案 4.检查备份 5.定期恢复演练 6.故障恢复策略 7.迁移升级 二、逻辑备份工具--mysqldump 1.介绍 2.使用场景 3.mysqldump命令的参数介绍 1&#xff09;全备&#xff1a; 2&#xff09;单库或…

YOLO 学习和使用 (重拾机器学习)

contents a nenrons 单层神经网络 多层神经网络 CNN (Convolutional Neural Network) YOLO 5.1. YOLO(you only look once) 5.2. predict stage: 置信度 * 类别条件概率 全概率非极大值抑制&#xff0c;通过IOU 指数进行实现每个 grid cell 生成两个预测 bounding box 无…

dsPIC单片机buck-boost拓扑双向DC-DC电源变换器设计

为实现电池储能装置的双向DC-DC变换器&#xff0c;本系统以buck-boost拓扑电路为核心&#xff0c;通过DSPICFJ256GP710单片机最小系统控制拓扑的切换&#xff0c;从而进行buck恒流充电和boost恒压放电。充电时效率≥94%&#xff0c;放电时效率≥95.5%&#xff0c;具有过压保护及…

JVM之【类加载机制】

一、类加载过程 1. 加载&#xff08;Loading&#xff09; 工作内容&#xff1a; 通过类的全限定名来获取定义此类的二进制字节流&#xff1a; JVM首先会调用类加载器的findClass方法来找到类文件的路径&#xff0c;通常从文件系统、JAR包、网络、数据库等来源获取类文件。 将…

Installing Tinyproxy on CentOS 7 测试可用

Installing Tinyproxy on CentOS 7 For RHEL/CentOS 7 systems, Tinyproxy is part of EPEL (Extra Packages for Enterprise Linux). Install EPEL on CentOS 7 yum install epel-release -y yum update -y Install Tinyproxy on CentOS 7 yum install tinyproxy -y 编辑…

Android单元测试实践

一、基础概念 按照Google官方建议,Android测试体系应该参照测试金字塔架构(如下图所示),App应该包含三类测试(即小型、中型和大型测试)。 图片 小型测试是指单元测试,用于验证应用的行为,一次验证一个类。中型测试是指集成测试,用于验证模块内堆栈级别之间的交互或相…