erase和remove

【整理完善】vector的erase和remove的区别 首先,vector中并没有remove成员方法,这里说的remove是STL算法中的remove函数 vector的erase和remove的区别 知道erase,以及存在的问题,会导致迭代器失效 ⁉️但remove原理真的忘记了,不知道 查找了下,remove是std中的算法,vector中没有该方法,两个区别挺大的,因为remove只是移动,并不删除 具体,看一下remove的实现就明白了:https://www.cplusplus.com/reference/algorithm/remove/ S 阅读详情
1.引言

       以下代码有什么问题,如何修改?

#include<iostream>
#include<vector>
using namespace std;

void print(vector<int>);//传引用不妥!!

int main()
{
	vector<int> array; 
	array.push_back(1);
	array.push_back(6);
	array.push_back(6);
	array.push_back(3);
//删除array中的所有的6
	vector<int>::iterator itor;
	vector<int>::iterator itor2;
	itor=array.begin();
	for (itor=array.begin();itor!=array.end();itor++;)
	{
		if (6==*itor)
		{
			itor2=itor;
			array.erase(itor2);
		}
	}
	print(array);
	return 0;
}

void print(vector<int> v)
{
	cout<<"\nvector size is: "<<v.size()<<endl;
}


 

2.vector中erase源码

       这段代码运行后容量只减小1,具体问题出在哪不知道。先看一下erase的源码。

iterator erase(iterator position) 
{
    if (position + 1 != end()) //若position不是指向最后一个元素
           copy(position + 1, finish, position); //运用的是copy,将删除位置的元素向后移动
    --finish;//vector中finish所指位置为end()返回值 
    destroy(finish);
    return position;
}
iterator erase(iterator first, iterator last) //允许last在first之前,后果自负
{
    iterator i = copy(last, finish, first);
destroy(i, finish);
finish = finish - (last - first);
    return first;
}


 

       现在知道了,如果这时删除一个元素之后,itor已经指向下一个元素,所以再调用itor++,那么连续的2个6就只能删除前一个。

       所以以上的for循环可以改为:

for (itor=array.begin();itor!=array.end();itor++;)
{
	if (6==*itor)
	{
		itor2=itor;
		array.erase(itor2);
		itor--;
	}
}


 

3.remove源码

       但是这样的代码可读性欠佳,还有一种改法就是更加规范的简洁的操作:调用算法remove,之后再进行erase。

       此时将for循环替代为:array.erase(remove(array.begin().array.end(),6),array.end());当然这个时候要包含头文件<algorithm>。

      

       为什么要删除,remove返回后的迭代器到vector末尾的元素呢?看remove算法源码。

      

       remove操作移除[first,last)之中所有与value相等的元素。这一算法并不真正从容器中删除那些元素(换句话说容器的大小并没有改变),而是将每一个不与value相等的元素轮番赋值给first之后的空间。返回值ForwardIterator标示出重新整理后的最后元素的下一个位置。例如序列{0,1,0,2,0,3,0,4},如果执行remove删除0,则结果是{1,2,3,4,0,3,0,4},返回值ForwardIterator指向第5个元素。所以如果要删除那些残余元素可以使用erase的两迭代器版本。源码如下:

tamplate<class ForwardIterator, class T>
ForwardIterator remove(ForwardIterator first, ForwardIterator last, const T& value)
{
	first=find(first, last, value);//找到第一个相等的元素
	ForwardIterator next = first;//以next标示出来
	//以下利用“remove_copy()允许新旧容器重叠”的性质,进行移除操作
	//并将结果置于原容器中
	return first == last ? first : remove_copy(++next,last,first,value);
}


        remove_copy并不改变原来的容器,只是将所要删除的值删除后,将新容器存储在result迭代器所指的位置处。

tamplate<class InputIterator, class OutputIterator, class T>
OutputIterator remove_copy(InputIterator first, InputIterator last, OutputIterator result, const T& value)
{
	for(;first != last;++first)
		if(*first != value)    //如果不相等
		{
			*result = *first;  //赋值给新容器
			++result;				
		}
	return result;
}


 

        当然remove函数也有仿函数版本的remove_if,remove_copy_if。

4.list中的remove和erase操作

       list中的erase:

iterator erase(iterator position)
{
	link_type next_node = link_typr(position.node->next);
	link_type prev_node = link_typr(position.node->prev);
	prev_node->next = next_node;
	next_node->prev = prev_node;
	destroy_node(position.node);
	return iterator(next_node);
}


 

        remove是算法库中的一个算法,但是list的结构使用这种remove算法时效率低下。根据list的结构,标准库专门为list设计了remove操作(其他容器是没有的)。

template<class T, calss Alloc>
void list<T,Alloc>::remove(const T& value)
{
	iterator first = begin();
	iterator last = end();
	while(first != last)
	{
		iterator next = first;
		++next;
		if(*first == value) erase(first);
		first = next;
	}
}


 

5.deque、set、map的erase操作

       待补充…………………..

 

 

vector erase和remove辨析 这里写自定义目录标题std::remove 位于 \std::remove 位于 <algorithm> std::vector::erase位于<vector> 两者字面意思都是删除(清除),但是实际操作上却有很大的差别。 iterator erase (const_iterator position):删除指定迭代器位置的元素,返回删除位置后一个位置的迭代器。 iterator erase (const_iterator first, const_iterator last): 阅读详情

相关推荐

Synopsys的CoreConsultant使用简析

CoreConsultant使用简析

weixin_58165606的博客 1万+

QT类学习系列(9)- Qt::QMap在for循环中使用erase的用法注意

QMap中erase后,itertator it指针已经被是否,再次调用将崩溃。erase函数返回指向删除后下一条数据的地址。 若使用for循环进行操作时,若内部使用erase操作,则it++操作需要放到函数体内部,与erase区别开来。 例如: Map中存入0-9的一一对应的映射,要删除其中的偶数项。 #include <QMap> #include <QDeb...

MatthewMao 2683

解锁笔记智能对话:手把手配置 Obsidian Copilot 插件与硅基流动模型

本文详细介绍了如何为Obsidian笔记软件配置Copilot插件,并接入硅基流动AI模型,从而为个人知识库添加智能对话能力。通过手把手教程,指导用户完成插件安装、API Key获取、模型配置及索引构建,最终实现基于个人笔记内容的深度语义问答,提升知识管理效率。

corn8的博客 612

Qt/C++工作笔记-对vector与QVector中erase操作的进一步认识(区别与联系)

VS代码如下:#include &lt;iostream&gt; #include &lt;vector&gt; using namespace std; void main(){ vector&lt;int&gt; intVec; for (int i = 0; i &lt; 10;i++){ intVec.push_back(i); } vector&lt;int&gt;:...

IT1995的博客 9242

Unity中URP下的菲涅尔效果实现(个性化修改)

在上篇文章中,我们实现了 URP 下的菲涅尔基础效果,我们在这篇文章中,对其进行自定义化修改。

楠溪泽岸的博客 2063

CSIT883系统分析与项目管理——Lecture3重点概念

🎈本节课,介绍了项目集成管理当中,关于NPV这个概念相关的内容,以及介绍什么是系统需求,什么时候需要开始系统需求,如何进行调查系统需求等等相关的题目,这里供大家复习参考吧!还有还有最关键的是NPV的计算,我单独写一篇博文,需要的同学快去学习吧!

AI手套的博客 1090

qt迭代器使用,遇上erase函数,程序崩溃

qt迭代器使用,遇上erase函数,程序崩溃 问题:在qlist用erase函数删除元素时候,发生程序崩溃。 经过测试发现 数组有多个元素,删除最后一个会程序崩溃 数组有多个元素,删除非最后一个不会程序崩溃 数组只有一个元素,删除最后一个不会程序崩溃 通过分析源码以及打印iterator发现 数组有多个元素,删除最后一个时,iterator it已经和list.end()一样了,再经过it++循环后,数组越界,导致程序崩溃 修改方法 在for循环最后一行追加容错 if(it == list.end

chen_227的博客 2628

C2f-DCN模块详解:可变形卷积与特征融合的完美结合

C2f模块作为YOLOv8的核心创新,代表了目标检测特征提取模块设计的最新进展。通过精简的卷积配置(仅2个基础卷积)、高效的特征重用设计(部分通道分割复用)、以及深层语义与浅层细节的协同建模能力,C2f在结构设计和性能表现上全面超越了前代的C3模块。与C3K2、C3K等变体相比,C2f在遮挡和密集环境下的检测鲁棒性更优,而C3K2和C3K分别在高速检测和多尺度检测方面有专门优化。这种差异化设计反映了YOLO系列模型向场景化、专业化发展的趋势。从设计原理角度看,C2f的核心优势在于其多路径梯度流动优化和。

浩瀚之水的专栏 378

Qt类 | QList类详解

QList是Qt框架中的一种泛型容器类,虽然是以数组列表(array-list)的形式实现的,但是在其前或后添加数据非常块。提供快速的基于索引的访问、插入和删除操作。Header:qmake:QT += core内存布局:QList内部可能以数组或指针数组的形式表示,具体取决于元素类型的大小和是否可移动。“是否可移动”通常指的是元素类型是否支持移动构造函数或移动赋值运算符。内存分配:QList在内部数组的两端预分配额外空间,以允许列表两端的快速增长。类型要求:QList的值类型必须是可赋值的效率。

zwcslj的博客 5338

2024年12月中国电子学会青少年软件编程(Python)等级考试试卷(六级)答案 + 解析

2024年12月中国电子学会青少年软件编程(Python)等级考试试卷(六级)答案 + 解析

伶俐角少儿编程 727

【KingSCADA】如何建立硬件系统及相关变量

本篇主要讲解如何定义设备,如何定义变量。KingSCADA3.8的采集系统是指负责和现场设备进行通讯,并采集现场数据和控制现场数据的模块,称之为采集器,也叫IOServer应用,它是一组独立的应用程序,可以脱离KingSCADA3.8软件,它依赖于KingSCADA3.8驱动产品,通过驱动与IO设备进行通讯。采集系统由通讯链路,设备,数据块组成。链路:链路是指计算机通过什么方式(接口)与设备进行连接,链路类别:串口,以太网,GPRS,Modem,通信卡,采集卡,无链路。

做有价值的事,积累有价值的笔记! 1万+

[QT_036]Qt学习之数据容器的迭代器

Qt学习之数据容器的迭代器

kongcheng253的博客 1928

pscad IEEE标准系统搭建说明

pscad IEEE标准系统搭建说明,包含典型的IEEE 9节点、14节点、30节点、39节点和118节点系统。内含标准测试系统的原始数据和潮流结果。

vector的remove和erase函数的区别

首先我们先来看一下两个函数 iterator erase(iterator position); iterator erase(iterator first, iterator last); erase: erase函数可以用于删除vector容器中的一个或者一段元素,在删除一个元素的时候,其参数为指向相应元素的迭代器,而在删除一段元素的时候,参数为指向一段元素的开头的迭代器以及指向结尾元...

xzymmd的博客 10万+

SIMATIC S7-1200, S7-1500 PID 控制[手册]

SIMATIC S7-1200, S7-1500 PID 控制[手册]

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

stl remove 和 erase

remove 和 erase

随便记点东西 630

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

stl list中erase和remove区别

list中remove和erase都是删除一个元素,其中remove参数类型和数据类型一致,而erase参数类型是迭代器。 remove(aim)是删除链表中的aim元素,若有多个aim,都会删除,而 erase(it)是删除迭代器指定位置的元素,并且返回下一个位置的迭代器来看例子。 #include &amp;lt;iostream&amp;gt; #include &amp;lt;list&amp;gt; using nam...

qq_42673507的博客 6553

C++ List的Remove和erase比较

Remove和erase都可以进行数据的移除,区别在于Remove移除的是List中所有与待移除项相等的数据,而erase移除的是迭代器所指的内容。 Remove有一个是否相等的比较,因此我们在Remove自定义的数据时,要添加“==”运算符的重载实现。 下面给出一个简单的演示例子: #include<iostream> #include<iterator> #include <list> using namespace std; #define R..

qq_31424423的博客 1337

C++ STL 中 remove 和 erase 的区别

C++ STL中的remove和erase函数曾经让我迷惑,同样都是删除,两者有什么区别呢? vector中的remove的作用是将等于value的元素放到vector的尾部,但并不减少vector的size vector中erase的作用是删除掉某个位置position或一段区域(begin, end)中的元素,减少其size list容器中的remove 成员函数,原型是

sfengsheng的专栏 1万+

erase和remove区别

在这个案例中,template只能用typename,这样在print函数中才可以用到模板,而且main函数中vector需要实例化为类型erase和remove的区别在于rease是真正删除了元素,迭代器不能再访问了 remove只是简单地把要remove的元素移到了容量的最后,迭代器还是可以访问的,不知道容器内部结构,所以无法做到真正删除template void print(vector

weixin_36429479的博客 9064

STL中remove()和erase()的用法

remove() 示例: initializer_list<int> list_t = { 1, 2, 1, 3, 4, 1, 5, 6, 7, 8 }; vector<int> vec(list_t); vector<int>::iterator it; for (it = vec.begin(); it != vec.end(); ++it){ cout ...

weixin_42057160的博客 397

c语言remove命令和erase,详解C++ list中erase与remove函数的使用

C语言中的erase与remove函数一直让小编很迷糊,因为他们的功能都是一样的,本文是详解C++ list中erase与remove函数的使用方法,接下来爱站技术频道小编带你一起来了解吧!erase的作用是,使作为参数的迭代器失效,并返回指向该迭代器下一参数的迭代器。如下:list ParticleSystem;list::iterator pointer;if(pointer->dead...

weixin_42131414的博客 1635

list中的erase和remove

erase的作用是,使作为参数的迭代器失效,并返回指向该迭代器下一参数的迭代器。 如下: [cpp] view plain copy print? list ParticleSystem;    list::iterator pointer;    if(pointer->dead == true)  {     pointer = ParticleSyst

shikelang_pp的博客 627

list容器的erase函数和remove函数

由于list容器的特殊实现,所以list容器实现了自己的erase函数和remove函数。erase函数的函数声明:可以看到函数的参数是由迭代器给出的。由迭代器给出删除的位置或者区间。    1) Removes from the list container either a single element (position) or a range of elements ([first,las...

ddou_pan的博客 2742

使用小细节——C++ list的erase和remove

文章目录1 erase(搭配迭代器)2 remove(搭配值) 平时一般使用都是vector,但是涉及到频繁删除元素的时候,就会用到list,因为vector每次删除后,删除元素后面的每个元素的迭代器都要重新分配。 1 erase(搭配迭代器) list<int> List; List.push_back(1); List.push_back(1); L...

韩江雪de 小屋 1万+

C++remove和erase

remove(str.begin(),str.end(),val); remove是将strz中等于val的值用后一个值覆盖,并返回最后一个未被删除的元素的下一个迭代器: 若str为"abcaad" 对'a'remove后则变为"bcdaaa" 配合erase可将所有a删除 str.erase(remove(str.begin(),str.end(),val),str.end()); ...

Hans的博客 1498

remove 和 erase 的区别

以容器vector来说明remove和erase的区别在STL中,vector容器也提供了remove()和erase()函数,用于从vector中删除元素。虽然这两个函数都可以实现删除元素的功能,但是它们之间还是有一些区别的。

一名大三才开始刷题的程序猿的刷题日记 1196
上一篇: 包含max(min)的栈及队列
下一篇: 指针与数组名
sicofield
博客等级 码龄18年 169粉丝 169原创
评论 4
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值