社区
C++ 语言
帖子详情
100分求STL解决办法~~
JeffHe
2006-03-24 05:37:43
偶使用的是VC6.0,使用STL时,碰到如下问题了:
已知一个vector和需要删除元素的下标位置,如何
用erase(remove_if(...))方式来完成该操作?
如:
vector<int> dd;//=[11 12 13 14 15 16 17 18 19]
现在要将dd下标为0,2,4的元素(即11,13,15)删除,
erase(remove_if(...))方式如何解决?是否需要使用
bind2nd()呢?
...全文
271
19
打赏
收藏
100分求STL解决办法~~
偶使用的是VC6.0,使用STL时,碰到如下问题了: 已知一个vector和需要删除元素的下标位置,如何 用erase(remove_if(...))方式来完成该操作? 如: vector dd;//=[11 12 13 14 15 16 17 18 19] 现在要将dd下标为0,2,4的元素(即11,13,15)删除, erase(remove_if(...))方式如何解决?是否需要使用 bind2nd()呢?
复制链接
扫一扫
分享
转发到动态
举报
写回复
配置赞助广告
用AI写文章
19 条
回复
切换为时间正序
请发表友善的回复…
发表回复
打赏红包
睡在床板下_
2006-03-25
打赏
举报
回复
ugg(逸学堂(exuetang.net)) ( ) 信誉:100 2006-03-24 19:58:00 得分: 0
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
it = erase(it);
}
----------------------------------
差不多了~~
xlsue
2006-03-25
打赏
举报
回复
我好像没发现有这个函数哦!
我认为可以这样:vector的iterator是随机的,可以使用iterator+下标,从vector的后面往前面移除下标为4,2,0的元素。
我也想看到更好的办法,期待中。。。
JeffHe
2006-03-25
打赏
举报
回复
xlsue(小林):是以下标进行删除~~ 而不是以值进行删除,
不知道如何在remove_if()中访问到vector[]的下标呢?
xlsue
2006-03-25
打赏
举报
回复
我觉得计数器和下标都差不多是同个意思,没有必要砖牛角尖吧?能达到程序意图的可以了
xlsue
2006-03-25
打赏
举报
回复
to 回复人:ricky460(阿酷):
你的程序符合楼主的,学习。
template <typename T>
void PRINT(const T& t)
{
for(typename T::const_iterator iter = t.begin() ; iter != t.end() ; ++ iter)
//这里前面要加typename
{
cout << *iter << " " ;
}
}
ricky460
2006-03-25
打赏
举报
回复
------------------------------------------------------------------------
JeffHe(雅永紫) ( ) 信誉:99 2006-03-25 08:56:00 得分: 0
xlsue(小林):是以下标进行删除~~ 而不是以值进行删除,
不知道如何在remove_if()中访问到vector[]的下标呢?
---------------------------------------------------------------------------
利用distance函数可以通过iterator得到下标 .
vector<int>::iterator iter ;
...........
int iIndex = distance(vInt.begin() , iter); //根据iterator得到索引 . . .
示例代码 :( 利用distance来删除制定下标元素)
int iOffset = 0 ;
for(vector<int>::iterator iter = vInt.begin() ; iter != vInt.end() ; ++ iter)
{
int iIndex = distance(vInt.begin() , iter) + iOffset;
if(iIndex == 0 || iIndex == 2 || iIndex == 4)
{
vInt.erase(iter , iter + 1);
iOffset += 1 ;
}
}
注解: 1: 这里加了一个变量iOffset , 这是因为 , 你在数组里删除一个元素 , 那么删除前下标2的元素 就对应于 删除后 下标1 的元素 . . . 每删除一个 ,就要累加一次 . .
2: 这段代码是有漏洞的 , 但是为了让楼主看得清晰明白 , 我没有加入纠错的代码.这里
需要加入判断是否是删除最后一个元素的代码 , 删除最后一个元素时 ,需要用另外的代码 . 代码很简单 ,就当是功课 , 让楼主自己写吧 . . .
3: 替代方法 :
int iIndex = 0 ;
for(.................)
{
if(iIndex == 0 || iIndex == 2 || iIndex == 4) DoSomething();
iIndex ++ ;
}
这种方法是最简单的 ,但我想 , 这并非是楼主所想要的 . . .
ricky460
2006-03-25
打赏
举报
回复
问题: 已知 vector , 和下标 , 利用erase , remove_if 删除元素 .
解决代码:
--------------------------------------------
#include "stdafx.h"
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std ;
//打印函数
template <typename T>
void PRINT(const T& t)
{
for(T::const_iterator iter = t.begin() ; iter != t.end() ; ++ iter)
{
cout << *iter << " " ;
}
}
//设置删除条件的仿函数
class DEL
{
int iIndex ; //定义一个iIndex来模拟vector的索引.
public:
DEL(){ iIndex = 0 ; }
bool operator()(int )
{
bool bReturn = (iIndex == 0 || iIndex == 2 || iIndex == 4) ;
iIndex ++ ;
return bReturn ;
}
};
int main(int argc, char* argv[])
{
vector <int> vInt ;
for(int i = 11 ; i <= 19 ; i ++) vInt.push_back(i);
PRINT(vInt);
cout << endl << endl;
vInt.erase(remove_copy_if(vInt.begin() , vInt.end() , vInt.begin(), DEL()), vInt.end());
PRINT(vInt);
return 0;
}
----------------------------------------------
{ 如上代码在 VC6 ,WindowXP 下测试成功 }
注解:
1: 用了一个条件判断仿函数DEL , 在DEL中定义了一个iIndex来模拟vector的索引 , 在
vInt.erase中 , vInt每向后移动一个元素 , 就会调用一次 DEL.operator()(int );
DEL.iIndex就会递增一次 , 即 , iIndex是跟实际vector的索引是相符的 . . . . .
2: 这里用remove_copy_if来代替remove_if ,是因为,STL中 , remove_if 是一个比较特殊的
函数 , 它会在内部调用两次传进去的比较函数 . 即内部类似于:
remove_if(....)
{
find_if(.... , DEL)
.......
return remove_copy_if(.... , DEL) ;
}
由于DEL是传递值而非传地址 ,所以这里在计算iIndex会出现问题 . 所以 , 在这里我用
remove_copy_if来代替了remove_if . 楼主可以不用考虑这些具体细节 . . .
以上代码可以实现楼主的需求. 楼主可以修改一下,以满足动态传入删除元素的下标的需求 .
howyougen
2006-03-24
打赏
举报
回复
guangmingshizhe(流云飞翼) ( ) 说的对
删除一个元素后,元素的下标已经发生改变了,这是问题所在吧
using namespace std;
struct mycond
{
mutable int i;
mycond(){i=-1;}
bool operator()(int) const
{
i++;
return (i%2 == 0) && (i<5) ;
}
};
int main()
{
//0,2,4的元素(即11,13,15)删除
int a[] = {11, 12, 13, 14, 15, 16, 17, 18, 19};
vector<int> dd(a, a + sizeof(a)/sizeof(a[0]) );//=[11 12 13 14 15 16 17 18 19]
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
cout<< *it<< " ";
}
cout<< endl;
replace_if(dd.begin(), dd.end(), mycond(),-1234567); //先替换成-1234567
dd.erase(remove(dd.begin(),dd.end(),-1234567),dd.end()); //再删除
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
cout<< *it<< " ";
}
cout<< endl;
system("pause");
}
guyanhun
2006-03-24
打赏
举报
回复
dd.erase(remove_if(dd.begin(), dd.end(),compose2( std::logical_and<bool>(),std::bind2nd(std::modulus<int>() ,2),std::bind2nd(std::less<int>(),16) ) ), dd.end());
guyanhun
2006-03-24
打赏
举报
回复
dd.erase(remove_if(dd.begin(), dd.end(),compose2( logical_and<bool>(),bind2nd(modulus<int>() ,2),bind2nd(less<int>(),16) ), dd.end());
xlsue
2006-03-24
打赏
举报
回复
ugg(逸学堂(exuetang.net)) ( ) 信誉:100 2006-03-24 19:58:00 得分: 0
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
it = erase(it);
}
------------------------------------------
打断一下,上面的代码是啥意思? 有erase(Iterator)这个函数?上面的代码好像有bug哦?
xlsue
2006-03-24
打赏
举报
回复
不明白楼主是想以下标0,2,4删除还是以值删除?
逸学堂
2006-03-24
打赏
举报
回复
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
it = erase(it);
}
xiaocai0001
2006-03-24
打赏
举报
回复
MSDN上的一个例子:
......
Numbers[0] = 10 ;
Numbers[1] = 20 ;
Numbers[2] = 10 ;
Numbers[3] = 15 ;
Numbers[4] = 12 ;
Numbers[5] = 7 ;
Numbers[6] = 9 ;
Numbers[7] = 10 ;
cout << "Before calling remove_if" << endl ;
// print content of Numbers
cout << "Numbers { " ;
for(it = start; it != end; it++)
cout << *it << " " ;
cout << " }\n" << endl ;
// remove all elements from Numbers that <= 10
last = remove_if(start, end, bind2nd(less_equal<int>(), 10) ) ;
......
一般用remove_if操作时, 对容器内元素的值有条件判定的, 像你这样的只是对容器的下标操作时, 可以直接用迭代器找到对应的下标, 然后erase()就可以了
妍妍
2006-03-24
打赏
举报
回复
删除一个元素后,元素的下标已经发生改变了,这是问题所在吧
citywanderer2005
2006-03-24
打赏
举报
回复
remove_if(dd.begin(), dd.end(), greater)
表示删除整个vector中满足条件(即使greater函数为真)的元素,它的返回值是被删除元素后的第二个元素的iterator。因为remove不会改变vector的size,所以最后空留的空间由原vector中的最后几个元素填充,这里就要用erase删除后面的重复的元素。
citywanderer2005
2006-03-24
打赏
举报
回复
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
bool greater( int value )
{
return (value == 11 || value == 13 || value == 15);
}
int main()
{
//0,2,4的元素(即11,13,15)删除
int a[] = {11, 12, 13, 14, 15, 16, 17, 18, 19};
vector<int> dd(a, a + sizeof(a)/sizeof(a[0]) -1);//=[11 12 13 14 15 16 17 18 19]
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
cout<< *it<< " ";
}
cout<< endl;
dd.erase(remove_if(dd.begin(), dd.end(), greater), dd.end());
for(vector<int>::iterator it = dd.begin(); it != dd.end(); ++it)
{
cout<< *it<< " ";
}
cout<< endl;
}
jiezhi
2006-03-24
打赏
举报
回复
这样的问题还是看看STL Ref吧
expert2000
2006-03-24
打赏
举报
回复
好贴。我也不懂。正好学习学习
C++
STL
参考手册包括基础语法打不开手册的
解决办法
C++
STL
参考手册包括基础语法打不开手册的
解决办法
C++
STL
list 遍历删除出错解决方案
主要介绍了C++
STL
list 遍历删除出错解决方案的相关资料,这里对出错进行分析,并给出正确的解决方法,需要的朋友可以参考下
C++
STL
STL
实战开发精讲视频
STL
是一个高效的C++程序库,它被容纳于C++标准程序库(C++ Standard Library)中,该库包含了诸多在计算机科学领域里所常用的基本数据结构和基本算法。为广大C++程序员们提供了一个可扩展的应用框架,高度体现了软件...
Effective
STL
有时候,最容易的变通办法是使用另一个
STL
实现。附录B给一个这种情况的例子。实际上,
STL
用得越多,编译器和库实现的区别就越重要。程序员在设法让合法的代码编译时遇到困难,他们通常责备他们的编译器,但对于
STL
,...
浅谈c++
stl
迭代器失效的问题
下面小编就为大家带来一篇浅谈c++
stl
迭代器失效的问题。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧,祝大家游戏愉快哦
C++ 语言
64,650
社区成员
250,478
社区内容
发帖
与我相关
我的任务
C++ 语言
C++ 语言相关问题讨论,技术干货分享,前沿动态等
复制链接
扫一扫
分享
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++
技术论坛(原bbs)
社区管理员
加入社区
获取链接或二维码
近7日
近30日
至今
加载中
查看更多榜单
社区公告
请不要发布与C++技术无关的贴子
请不要发布与技术无关的招聘、广告的帖子
请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下
试试用AI创作助手写篇文章吧
+ 用AI写文章