set和map增删查改的使用

本文详细介绍了C++ STL中的set和map的使用,包括它们的内部实现(红黑树)、增删查改操作。set是存储唯一元素且自动排序的容器,不允许元素值重复;map是存储键值对并按键排序的容器,键必须唯一。文章还提到了multiset和multimap,允许元素或键的重复。示例代码展示了如何插入、查找、删除元素,以及通过operator[]修改map中的值。
摘要由CSDN通过智能技术生成

set的内部实现是基于红黑树,set就是以红黑树的格式存储内部的所有元素的。
set中的所有元素都会根据元素的键值自动被排序。set的元素不像map那样可以同时拥有实值(value)和键值(key)。set中只有一个值,set不允许两个元素有相同的值。
我们不可以使用迭代器修改set的元素值,元素值已经按照红黑树的方式排列好,如果修改就会改变其组织。set中,可以允许删除和增加一些元素。

map的内部实现同样是基于红黑树。
和set不同,map的所有元素都是一个键值对pair(key,value),所有元素都会按照key的值进行排序,map中不允许有相同的key值,但可以修改map中元素的value值。
而multiset和multimap的特性和set和map一样,唯一的差别是允许key重复
1 set和multiset
set和multiset会根据特定的排序准则,自动将元素进行排序。不同的是后者允许元素重复而前者不允许。
set和multiset两种头文件都为:#include<set>
set和multiset都是定义在std空间里的类模板。

template < class T,                        // set::key_type/value_type
           class Compare = less<T>,        // set::key_compare/value_compare
           class Alloc = allocator<T>      // set::allocator_type
           > class set;
template < class T,                        // multiset::key_type/value_type
           class Compare = less<T>,        // multiset::key_compare/value_compare
           class Alloc = allocator<T> >    // multiset::allocator_type
           > class multiset;

其中第二个参数来定义排序准则为仿函数,默认为less,也就意味着,默认遍历结果为升序。例:

    set<int,greater<int>> s1;
    s1.insert(10);
    s1.insert(3);
    s1.insert(9);
    s1.insert(8);
    s1.insert(1);
    s1.insert(3);

    set<int,greater<int>>::iterator it1 = s1.begin();
    while (it1 != s1.end())
    {
        cout << *it1 << "  ";
        ++it1;
    }
    cout << endl;

运行结果:
这里写图片描述
相关操作
这里写图片描述这里写图片描述
1.1 插入
插入用insert函数

pair<iterator,bool> insert (const value_type& val);//pair::first set to an iterator pointing to either the newly inserted element or to the equivalent element already in the set. The pair::second element in the pair is set to true if a new element was inserted or false if an equivalent element already existed.
iterator insert (iterator position, const value_type& val);//在指定的位置插入指定的数据,position是一个迭代器的位置,x表示的是要插入的数。如果插入成功的话,会返回一个插入新位置的迭代器。
template <class InputIterator>
void insert (InputIterator first, InputIterator last);//插入一个迭代器区间

pair是一种模板模型,每个pair可以存储两个值,这俩个值得类型是任意类型。定义在#include中,其标准形式为:template< class T1,class T2> struct pair;
pair有两个成员分别是first和second,set是一个模板,first是一个指向要插入位置的迭代器,如果second是false则first就是已经存在的元素的这个位置的迭代器,如果second为true,first就是要插入位置的迭代器。
结构如下:

template<class K,class V>
class pair
{
public:
    pair(const K& key, const V& v)
        :first(key)
        , second(v)
    {   }
    const K first;
    V second;
};

例:

set<int> myset;
set<int>::iterator it;
pair<iterator,bool> ret;
// 初始化
for (int i=1; i<=5; ++i) myset.insert(i*10);  
ret = myset.insert(20);  //20存在,插入失败 
if (ret.second==false) it=ret.first;  // it指向20
myset.insert (it,25);    
myset.insert (it,24);          
myset.insert (it,26);       
int myints[]= {
  5,10,15};   
myset.insert (myints,myints+3);
for (it=myset.begin(); it!=myset.end(); ++it)
      cout << ' ' << *it;
cout << '\n';

1.2 查找
查找用find()函数

iterator find(const key_type& x) const;//若找到返回该迭代器的位置,否则就返回的是最后一个元素后面的位置

使用count()函数

size_type count(const key_type& x)const;//count是为了统计某个数值出现的次数,在set里面不能重复出现相同的数值,count的返回值只有01两个值,0表示的是不存在,1表示存在。

例:

set<int> s3;
s3.insert(10);
s3.insert(3);
s3.insert(9);
s3.insert(8);
s3.insert(1);
s3.insert(3);
set<int>::iterator pos = s3.find(10);//当迭代器没找到返回end,end是最后一个数据的下一个
if (s3.count(8))
{
    cout << "exit" << endl;
}
else
{
    cout << "Non" << endl;
}

1.3 删除

void erase(iterator position)//删除一个迭代器位置
size_type erase(sonst key_type& x)//删除成功的话就返回1
void erase(iterator first, iterator last)//删除一段迭代器区间

例:删除一个迭代器位置

set<int> s3;
s3.insert(10);
s3.insert(3);
s3.insert(9);
s3.insert(8);
s3.insert(1);
s3.insert(3);
set<int>::iterator pos = s3.find(10);//当迭代器没找到返回end,end是最后一个数据的下一个
if (pos!=s3.end())
    s3.erase(pos);

例:删除一段迭代器区间

set<int> s4;
set<int>::iterator itlow, itup;
for (int i = 1; i<10; i++) s4.insert(i * 10); // 10 20 30 40 50 60 70 80 90
itlow = s4.lower_bound(35);          
itup = s4.upper_bound(65);
s4.erase(itlow, itup);
set<int>::iterator it4 = s4.begin();
while (it4 != s4.end())
{
    cout << *it4 << "  ";
    ++it4;
}
cout << endl;

1.4 multiset在set的基础上允许键值冗余
例:

multiset<int> s4;
s4.insert(10);
s4.insert(3);
s4.insert(9);
s4.insert(8);
s4.insert(1);
s4.insert(3);
multiset<int>::iterator it4 = s4.begin();
while (it4 != s4.end())
{
    cout << *it4 << "  ";
    ++it4;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值