STL(六)——map、multimap

STL——map、multimap


关联容器与map的介绍

所谓关联容器,是相对顺序容器而言,关联容器中的元素是按照关键字(KEY)l来保存和访问的(顺序容器是根据元素在容器中的位置来保存和访问的)。
关联容器中有两个最主要的类型:一个是map,另一个是set。map中的元素是键值对(key-value),其中键(key)用于索引关联的数值(value),set中只有key。
其中,在map,中键值对是以pair形式存储的,pair是标准库类型,定义在头文件utility中。pair保存两个数据成员,pair的数据是public的,两个成员分别是first和second,在map中,pair.first表示key,pair.second表示value。
⚠️map/multimap中的本身是有序的 是按key进行 升序排列的⚠️


map与set的异同

map与set的结构如图所示:
map与set的差异
⚠️map和set的Key不可变,set的元素是const的,map中pair的第一个元素是const的。


map与multimap的异同

map 与 multimap是存储key-value(键-值 对)类型的容器。
不同之处在于:map只允许key与 value一一对应;multimap一个key可对应多个value在这里插入图片描述
⚠️上述使其不同之处,下面如果,不作特别说明,适用于map的都适用于multimap(见代码)


map类对象的构造

    //map最基本的构造函数
    map<string,int> mp1;
    map<char,int> mp2;
    map<int,char> mp3;
    map<int,string> mp4;
    map<double,int> mp5;

map添加元素

    //map的添加元素
    
        //第一个pair添加法
    mp1.insert(pair<string,int>("aaa",100));
    mp2.insert(pair<char,int>('a',100));
    mp3.insert(pair<int,char>(100,'b'));
    mp4.insert(pair<int,string>(100,"BBB"));
    mp5.insert(pair<double,int>(0.1,200));
    
         //第二种添加元素的方法 make_pair()
    map<string,int> mp;
    mp.insert(make_pair("AA",100));
    map<int,double> mmp;
    mmp.insert(make_pair(1,0.2));

        //第三种临时map对象value_type添加元素法
    mp1.insert(map<string,int>::value_type("bbb",200));
    mp2.insert(map<char,int>::value_type('b',100));
    mp3.insert(map<int,char>::value_type(100,'b'));
    mp4.insert(map<int,string>::value_type(100,"BBB"));
    mp5.insert(map<double,int>::value_type(0.2,400));
    
        //map中最简单常用的添加元素方法(类似于数组的赋值)
            //这个非常方便啊,如果 mp1对象中无"one"键值时创建one键值,若已经有 one键值,则可以对键所对应的值,!!!!进行修改、赋值!!!!!
    mp1["one"] = 1;
    mp2['a'] = 100;
    mp3[1] = 'c';
    mp4[10] = "EEE";
    mp5[0.2] = 200;

map元素的遍历

    //map元素的遍历
    for(map<string,int>::iterator it = mp1.begin();it != mp1.end();it++)
    {
        cout<<it->first<<" "<<it->second<<endl;
    }

map元素的查找、更改、删除

    //map元素中的查找 find函数 返回一个指向键的值为key的元素的迭代器,如果没有找到返回指向超尾的迭代器
    map<string,int>::iterator mit = mp1.find("aaa");
    if(mit != mp1.end())	//mit 不指向超尾,成功找到
        cout<<mit->second<<endl;    //注意这里的 mit指针必须用“ -> ” 来访问second函数,且该函数是没有括号的
    else
        cout<<"Sorry\n";
    map<double,int>::iterator it_5 = mp5.find(0.2);
    if(it_5 != mp5.end())
        cout<<it_5->first<<" "<<it_5->second<<endl;
    it_5->second = 999;     //可以修改键所对应的 的值
        cout<<it_5->first<<" "<<it_5->second<<endl;
    //it_5->first = 0.3;    //但是去不可以,更改 键 值
        //cout<<it_5->first<<" "<<it_5->second<<endl;

    //map中元素的删除 erase(指向键值的指针) //删除该指针指向的元素
    //mp5.erase(it_5);
    map<double,int>::iterator it =mp5.find(0.2);
    if(it == mp5.end()) // 如果it指向mp5.end()
        cout<<"成功删除it_5指向的元素"<<endl;

map容器间元素的交换

    //同类型map的容器内容的交换
    map<string,int> m1;
    map<string,int> m2;
    map<string,int> m3;
    map<string,int> m4;
    m1.insert(pair<string,int>("A",100));
    m1.insert(map<string,int>::value_type("B",200));
    m1["C"] = 200;
    m1["C"]++;  //使 m1["C"] 的value值增加一,此时m1["A"] = 201;
    m2.insert(pair<string,int>("X",777));
    m2.insert(map<string,int>::value_type("Y",888));
    m2["Z"] = 999;
    m2["Z"]++; //使 m1["Z"] 的value值增加一,此时m2["Z"] = 1000;

    m1.swap(m2);    //此时 m1于m2的内容进行交换,⚠️该函数只能对两个容器的内容进行交换


    for(map<string,int>::iterator it = m1.begin(); it != m1.end();it++)
        cout<<it->first<<" "<<it->second<<endl;

map中常用函数

    //map中常见的函数
    	//1. begin(), end();
        
        //2. rbegin(), rend();
        
        //3. clear() 清除容器中所有元素
        
        //4. count(参数类型为:key) 返回map中的某个值的数量
            cout<<endl;
            cout<<"m1.count: "<<m1.count("Z")<<endl;    //输出键为"Z"的值
            
        //5. empty() 容器为空返回true
        
        //6. equal_range() 返回特殊条目的迭代器
        pair<map<string,int>::iterator,map<string,int>::iterator> pir = m1.equal_range("X");
        cout<<pir.first->first<<" "<<pir.first->second;
        cout<<pir.second->first<<" "<<pir.second->second;
        
        //7. size() 返回容器元素的个数
        
        //8.  比较两个key值的大小函数、value_comp() 比较map元素 值value 的函数
        
        //8. lower_bound(参数:key) 返回指向 >=key 的第最后一个满足大于等于键的位置的迭代器
        	 upper_bound(参数:key)返回指向 >key 的第一个大于key的位置的迭代器
        map<string,int> mm1;
    	mm1["AAA"] = 1;mm1["BBB"] = 2;mm1["CCC"] = 3;
    	mm1["DDD"] = 4;mm1["AAA"]--;
    	cout<<mm1.upper_bound("CCC")->first<<" "<<mm1.upper_bound("CCC")->second<<endl;
    	cout<<mm1.lower_bound("CCC")->first<<" "<<mm1.lower_bound("CCC")->second<<endl;
    	/*输出:
      	DDD 4
      	CCC 3
     	*/


multimap实例应用讲解

class Person
{
public:
    string name;
    int age;
    string tel;
    int salary;
};

    Person p1,p2,p3,p4,p5;
    p1.name = "A";p1.age = 10;
    p2.name = "B";p2.age = 11;
    p3.name = "C";p3.age = 12;
    p4.name = "D";p4.age = 13;
    p5.name = "E";p5.age = 14;
    //
    multimap<string,Person> mp;
    mp.insert(make_pair("Sale",p1));
    mp.insert(make_pair("Sale",p2));    //⚠️这里 mp 如果不是multimap的这一条指令会插入失败(因为键值重复)
    mp.insert(make_pair("Development",p3));
    mp.insert(make_pair("Development",p4));//⚠️这里 mp 如果不是multimap的这一条指令会插入失败
    mp.insert(make_pair("Fiancial",p5));

    //遍历
    for(map<string,Person>::iterator it = mp.begin(); it != mp.end() ; it++)
    {
        cout<<it->first<<"\t"<<it->second.name<<"\t"<<it->second.age<<endl;
    }

    //计算键为 Development 的元素的个数
    int num = mp.count("Development");
    cout<<num<<endl;
    //查看、更改元素值(通过迭代器直接访问地址进行修改)
        //例1:输出键为 Development 元素的值
    map<string,Person>::iterator it_1 = mp.find("Development");
    while(num--)
    {
        cout<<it_1->first<<"\t"<<it_1->second.name<<"\t"<<it_1->second.age<<endl;
        it_1++;
    }

        //例2:更改键值为 Sale 的值的名字
    for(map<string,Person>::iterator it = mp.begin(); it != mp.end() ; it++)
    {
        if(it->first == "Sale")
            it->second.name = "Sale_" + it->second.name;
        //输出修改后的结果
        cout<<it->first<<"\t"<<it->second.name<<"\t"<<it->second.age<<endl;
    }

特别提醒

map的sort问题,map中的元素是按键key进行升序排序的,所以不能对map用sort函数

map更深入探究

STL——map源码剖析(传送门)


发布了73 篇原创文章 · 获赞 100 · 访问量 2712

猜你喜欢

转载自blog.csdn.net/qq_34261446/article/details/103462747