stl map与multimap的使用

map是STL的一个关联容器,它提供一对一(其中第一个可以称为关键字,每个关键字只能在map中出现一次,第二个称为该关键字的值)的数据处理能力,由于这个特性,它完成有可能在我们处理一对一数据的时候,在编程上提供快速通道。这里说下map内部数据的组织,map内部自建一颗红黑树(一 种非严格意义上的平衡二叉树),这颗树具有对数据自动排序的功能,所以在map内部所有的数据都是有序的,后边我们会见识到有序的好处。

multimap:允许关键值重复,重复的关键值可以有不同的val,map不允许关键值重复。

C++ map是一种关联式容器,包含“关键字/值”对

头文件
#include<map>

变量定义
map<int,int> m;

主要函数

begin() 返回指向map头部的迭代器
clear() 删除所有元素
count() 返回指定元素出现的次数
empty() 如果map为空则返回true
end() 返回指向map末尾的迭代器
equal_range() 返回特殊条目的迭代器对
erase() 删除一个元素
find() 查找一个元素
get_allocator() 返回map的配置器
insert() 插入元素
lower_bound() 返回键值>=给定元素的第一个位置
rbegin() 返回一个指向map尾部的逆向迭代器
rend() 返回一个指向map头部的逆向迭代器
size() 返回map中元素的个数
upper_bound() 返回键值>给定元素的第一个位置

实例一

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
#include<iostream>
#include<map>
using namespace std;
int main()
{
    map<int,string> map1;//定义
    map1[13]="beijing";//添加元素key:13,val:beijing
    map1.insert(map<int,string>::value_type(2,"xian"));//添加元素key:2,val:xian
    map1.insert(pair<int,string>(1,"china"));
    map1.insert(make_pair<int,string>(4,"V5"));
    map<int,string>::iterator it;
    //map自动按key的值进行排序
    for (it=map1.begin();it!=map1.end();it++)
   {
        cout<<it->first<<":"<<it->second<<" ";
    }
    cout<<endl<<"-------"<<endl;
    map1[13]="this";//修改key为13val为this
    map1.insert(pair<int,string>(1,"China"));//不会修改key为1的val
    map1.insert(make_pair<int,string>(4,"V6")); //不会修改
    map1.insert(map<int,string>::value_type(2,"Xian"));//不会修改
    for (it=map1.begin();it!=map1.end();it++)
    {
         cout<<it->first<<":"<<it->second<<" ";//it->first获取key的值,it->second获取val的值
    }
    cout<<endl<<"-------"<<endl;
    cout<<map1.find(1)->second<<endl;
    //cout<<map1.find(19)->second<<endl; 注意这里没有key为19的值,故运行时会出错
    //因此查找key的val值正确的做法应为
    it=map1.find(19);
    if(it==map1.end())
    {
        cout<<"No found"<<endl;//没有查找成功时   
    }
    else
    {
        cout<<it->second<<endl;
    }
    it=map1.find(1);
    if(it==map1.end())
    {
         cout<<"No found"<<endl;//没有查找成功时  
     }
    else
    {
         cout<<it->second<<endl;
    }
    it=map1.lower_bound(2);
    if (it!=map1.end())
    {
         cout<<it->first<<":"<<it->second<<endl;
    }
    it=map1.upper_bound(2);
    if (it!=map1.end())
    {
         cout<<it->first<<":"<<it->second<<endl;
    }
    map1.erase(2);
    for (it=map1.begin();it!=map1.end();it++)
    {
         cout<<it->first<<":"<<it->second<<" ";//it->first获取key的值,it->second获取val的值
    }
    cout<<endl<<"-------"<<endl;
    map1.erase(8);
    for (it=map1.begin();it!=map1.end();it++)
    {
           cout<<it->first<<":"<<it->second<<" ";//it->first获取key的值,it->second获取val的值
     }
     cout<<endl<<"-------"<<endl;
     return 0;
}

实例二

1)根据要删除的键值对位于容器中的位置,实现删除该键值对。
//删除map容器种指定位置的键值对
iterator erase(const_iterator position);
其中,position为迭代器,指向要删除的键值对。
该方法会返回一个iterator迭代器,其指向的是删除键值对之后的那个键值对(如果是删除最后一个键值对,那么该方法也会返回迭代器指向的最后一个键值对之后的位置)。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include<iostream>
#include<map>
#include<string>
using namespace std;
int main()
{
    //创建并初始化map容器
    map<string,int> myMap{{"penny",1},{"leonard",2},{"sheldon",3},{"howard",4}};
    cout<<myMap.size()<<endl; //输出键值对个数
    //遍历map容器
    for(auto iter = myMap.begin(); iter != myMap.end(); iter++){
        cout<<iter->first<<","<<iter->second<<"  ";
    }
    cout<<endl;
    //创建一个指向要删除键值对的迭代器
    map<string,int>::iterator iter = ++myMap.begin(); //指向第二个键值对
    //执行删除操作
    map<string,int>::iterator ret = myMap.erase(iter);
    cout<<myMap.size()<<endl; //输出键值对个数
    //输出erase()方法返回的迭代器指向的键值对
    cout<<ret->first<<" "<<ret->second<<endl;
    return 0;
}

实例三

2)传入要删除目标键值对的键的值,该方法会自行根据指定的键找到目标键值对,并将其删除。
//删除map容器种键为k的键值对
size_type erase(const key_type& k);
其中,参数k为要删除的键值对的键的值。
该方法的返回值为成功删除的键值对的个数。由于map容器种每个键值对的键都是独一无二的,故其返回值最大为1.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#include<iostream>
#include<map>
#include<string>
using namespace std;
int main()
{
    //创建并初始化map容器
    map<string,int> myMap{{"penny",1},{"leonard",2},{"sheldon",3},{"howard",4}};
    cout<<myMap.size()<<endl; //输出键值对个数
    //执行删除操作,删除myMap容器种键为"penny"的键值对
    int num = myMap.erase("penny");
    cout<<myMap.size()<<endl; //输出键值对个数
    //输出erase()方法的返回值
    cout<<"num= "<<num<<endl;
    return 0;
}

实例四

3)在某些情况下,可能需要删除某个指定区域内的所有键值对,也可以通过erase()方法实现。
//删除 map 容器中位于 [first,last) 区域内的所有键值对
iterator erase (const_iterator first, const_iterator last);
其中参数first和last都是迭代器,[first, last)就表示map容器种的某个范围,该方法会删除此范围内的所有键值对。
返回值为一个迭代器,其指向删除范围之后的第一个键值对。如果该范围之后,不再有任何键值对,则返回的迭代器指向map容器最后一个键值对之后的位置。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include<iostream>
#include<map>
#include<string>
using namespace std;
int main(){
    //创建并初始化map容器
    map<string,int> myMap{{"penny",1},{"leonard",2},{"sheldon",3},{"howard",4}};
    cout<<myMap.size()<<endl; //输出键值对个数
    //指定范围
    map<string,int>::iterator first = myMap.begin();
    map<string,int>::iterator last = --myMap.end();
    //删除指定范围内的容器
    map<string,int>::iterator ret = myMap.erase(first,last);
    cout<<myMap.size()<<endl;
    cout<<ret->first<<" "<<ret->second<<endl;
    return 0;
}

实例五:
insert插入相同键值时不会改变原有的值

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
#include<bits/stdc++.h>
using namespace std;
map<int,int> ma;
int main()
{
    int n;
    cin>>n;
    for (int i=1;i<=n;i++)
    {
        int x,y;
        cin>>x>>y;
        ma.insert(pair<int,int> (x,y)); //插入相同键值的时候不会改变
        map<int,int>::iterator it;
        for (it=ma.begin();it!=ma.end();it++)
        {
            cout<<(it->first)<<" "<<(it->second)<<endl;
        }
        cout<<"----"<<endl;
    }
}
/*
in
8
4 5
4 3
1 2
3 7
3 8
8 9
4 0
5 6
out
8
4 5
----
4 5
----
1 2
4 5
----
1 2
3 7
4 5
----
1 2
3 7
4 5
----
1 2
3 7
4 5
8 9
----
1 2
3 7
4 5
8 9
----
1 2
3 7
4 5
5 6
8 9
----
*/

使用数组形式可以改变原有的值

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include<bits/stdc++.h>
using namespace std;
map<int,int> ma;
int main()
{
    int n;
    cin>>n;
    for (int i=1;i<=n;i++)
    {
        int x,y;
        cin>>x>>y;
        ma[x]=y; //数组方式可以修改原有的值
        map<int,int>::iterator it;
        for (it=ma.begin();it!=ma.end();it++)
        {
            cout<<(it->first)<<" "<<(it->second)<<endl;
        }
        cout<<"----"<<endl;
    }
}
/*
in
8
4 5
4 3
1 2
3 7
3 8
8 9
4 0
5 6
out
4 5
----
4 3
----
1 2
4 3
----
1 2
3 7
4 3
----
1 2
3 8
4 3
----
1 2
3 8
4 3
8 9
----
1 2
3 8
4 0
8 9
----
1 2
3 8
4 0
5 6
8 9
----
*/

multimap不支特数组的插入形式
map使用结构体的实例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
//当元素为结构体时自定义排序
#include <iostream> 
#include <map>    
#include <utility>
using namespace std;
struct Info
{
    string name;
    float score;
    //重载"<"操作符,自定义排序规则
    bool operator < (const Info &a) const
    {
        if(score==a.score)
            return name>a.name;
        return score>a.score;
    }
};
int main()
{
  
    map<Info,int> m;
    Info info;
    info.name="Jack";
    info.score=60;
    m[info]=25;
    info.name="Tom";
    info.score=60;
    m[info]=30;
    info.name="Bomi";
    info.score=80;
    m[info]=10;
    info.name="Peti";
    info.score=66.5;
    m[info]=30; 
    map<Info,int>::iterator it;
    for(it=m.begin();it!=m.end();it++)
    {
        cout<<(*it).second<<" : ";
        cout<<((*it).first).name<<" "<<((*it).first).score<<endl;
    }
    return 0;
}

  

 

posted @   心悟&&星际  阅读(140)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· C#/.NET/.NET Core优秀项目和框架2025年2月简报
· Manus爆火,是硬核还是营销?
· 一文读懂知识蒸馏
· 终于写完轮子一部分:tcp代理 了,记录一下
点击右上角即可分享
微信分享提示