C++中的map和multimap容器
2016-07-17 16:24
316 查看
map和multimap是两种关联容器,他们的元素是一些关键字——值(key-value)对:关键字起索引作用,值则表示与索引相关联的数据。它们的元素都是以键为标准进行的strict weak ordering(严格弱序化)的排序。
既然前面说了,map是以键的严格弱序化进行排序的,那么有必要对严格弱序化进行说明,按照维基所说:
严格弱序化具有下面的特性,假设x和y是属于S的元素
1. For all x, it is not the case that x < x (irreflexivity).(即在stl的算法函数中若两个相同的容器对象做比较,返回false)
2. For all x ≠ y, if x < y then it is not the case that y < x (asymmetric).
3. For all x, y, and z, if x < y and y < z then x < z (transitivity).
4. For all x, y, and z, if x is incomparable with y, and y is incomparable with z, then x is incomparable with z (transitivity of equivalence).
参数说明:
comp:是一个二元谓词,比较两个元素的大小关系,并且这个二元谓词是严格弱序化定义的,如果comp不指定的话,默认为使用标准库的
alloc:分配器对象
first,last:两个map的迭代器,表示范围[first,last]
x表示一个map对象
构造函数的使用例子:
特别注意,当使用函数对象的时候,只需要在模板类型中指明函数对象类型就行,但是使用函数指针的时候,除了在模板类型中指明,还要在构造函数中使用。
可以通过
4000
器和尾后迭代器。
可以通过
上面first表示key,second表示value。
需要解释一下[]和
第一个函数利用迭代器指向删除的元素。
其中第二个函数返回删除元素的个数,若键k在map中存在,则返回1,否则返回0(map中相同键只有一个)。
第三个函数删除范围[first, last)中的元素。
第四个表示清空map。
查找元素利用键k去查找,找到的话返回指向该元素的迭代器,没有找到的话就返回
这个函数返回键k在map中出现的次数,由于map中相同键只能出现一次,因此返回值最大为1。
运行结果:
elements in mymap:
a => 50
c => 150
d => 200
运行结果如下:
![](https://img-blog.csdn.net/20160717164713943)
get_allocator() 返回map的配置器
key_comp() 返回比较元素key的函数
lower_bound() 返回键值>=给定元素的第一个位置
upper_bound() 返回键值>给定元素的第一个位置
size() 返回map中元素的个数
multimap的元素类型和map是一致的,这里就不在赘述。
这里就简要概述一下multimap和map不同的地方:multimap中相同的键可以多次出现,而不像map只能出现一次。
在multimap中没有定义[]运算符,当然也没有定义at()成员函数,因此,multimap进行插入的时候,只能利用insert()函数进行插入。
map
首先先介绍一下map的元素类型:map::key_type这个是map的关键字的类型。
map::mapped_type这个是与关键字相关的值的类型。
value_type这个类型是map中整个键值对的类型,其实它是下面的定义
typedef pair<const Key, T> value_type。
既然前面说了,map是以键的严格弱序化进行排序的,那么有必要对严格弱序化进行说明,按照维基所说:
严格弱序化具有下面的特性,假设x和y是属于S的元素
1. For all x, it is not the case that x < x (irreflexivity).(即在stl的算法函数中若两个相同的容器对象做比较,返回false)
2. For all x ≠ y, if x < y then it is not the case that y < x (asymmetric).
3. For all x, y, and z, if x < y and y < z then x < z (transitivity).
4. For all x, y, and z, if x is incomparable with y, and y is incomparable with z, then x is incomparable with z (transitivity of equivalence).
构造函数
构造函数有很多类型,可以构造一个空map,也可以用一个迭代器范围构造,还可以使用初始化列表进行构造。并且在构造函数中我们还可以利用函数指针或者函数对象作为参数来制定键的排列顺序。// 构造空map explicit map (const key_compare& comp = key_compare(), const allocator_type& alloc = allocator_type()); explicit map (const allocator_type& alloc); // 利用迭代器范围构造 template <class InputIterator> map (InputIterator first, InputIterator last, const key_compare& comp = key_compare(), const allocator_type& = allocator_type()); // 拷贝构造函数 map (const map& x); map (const map& x, const allocator_type& alloc); // 列表构造 map (initializer_list<value_type> il, const key_compare& comp = key_compare(), const allocator_type& alloc = allocator_type());
参数说明:
comp:是一个二元谓词,比较两个元素的大小关系,并且这个二元谓词是严格弱序化定义的,如果comp不指定的话,默认为使用标准库的
less.
alloc:分配器对象
first,last:两个map的迭代器,表示范围[first,last]
x表示一个map对象
构造函数的使用例子:
#include <iostream> #include <map> bool fncomp (char lhs, char rhs) {return lhs<rhs;} struct classcomp { bool operator() (const char& lhs, const char& rhs) const {return lhs<rhs;} }; int main () { std::map<char,int> first; first['a']=10; first['b']=30; first['c']=50; first['d']=70; std::map<char,int> second (first.begin(),first.end()); std::map<char,int> third (second); std::map<char,int,classcomp> fourth; // class as Compare bool(*fn_pt)(char,char) = fncomp; std::map<char,int,bool(*)(char,char)> fifth (fn_pt); // function pointer as Compare return 0; }
// 列表构造 map<string, string> authors = { {"Joyce", "James"}, {"Austen", "Jane"}, {"Dickens", "Charles"} }
特别注意,当使用函数对象的时候,只需要在模板类型中指明函数对象类型就行,但是使用函数指针的时候,除了在模板类型中指明,还要在构造函数中使用。
map的迭代器
map可以通过迭代器进行遍历,而且它的迭代器是双向迭代器,可以前后移动。可以通过
begin()和
end()获得开始迭代
4000
器和尾后迭代器。
可以通过
cbegin()和
cend()获得
const_iterator,即通过迭代器不能修改元素的值。
map<int, int> mm(first, last); map<int, int>::iterator it = mm.begin(); for(; it != mm.end(); it++) cout << it->first << " " << it->second << endl;
上面first表示key,second表示value。
添加、删除、查找元素
添加元素
添加元素可以分为添加单个元素或者范围添加map<string, int> words; // 方式1 words.insert(pair<string, int>("apple", 3)); // 方式2 words.insert(map<string, int>::value_type("apple", 3)); // 方式3 words["apple"] = 3; // 方式4 words.at("apple") = 3; //范围添加 template <class InputIterator> void insert (InputIterator first, InputIterator last); void insert (initializer_list<value_type> il);
需要解释一下[]和
at()添加元素的方式,当键在map中不存在的时候,这两条语句相当于添加元素。但是当map中存在所指键的时候,只是将键的对应的value进行改变。
at()比起[]的优点在于当传进的参数和键的类型不同的时候,
at()会抛出异常。
删除元素
iterator erase (const_iterator position); size_type erase (const key_type& k); iterator erase (const_iterator first, const_iterator last); void clear();
第一个函数利用迭代器指向删除的元素。
其中第二个函数返回删除元素的个数,若键k在map中存在,则返回1,否则返回0(map中相同键只有一个)。
第三个函数删除范围[first, last)中的元素。
第四个表示清空map。
查找元素
iterator find (const key_type& k); const_iterator find (const key_type& k) const;
查找元素利用键k去查找,找到的话返回指向该元素的迭代器,没有找到的话就返回
map::end。
size_type count (const key_type& k) const;
这个函数返回键k在map中出现的次数,由于map中相同键只能出现一次,因此返回值最大为1。
#include <iostream> #include <map> int main () { std::map<char,int> mymap; std::map<char,int>::iterator it; mymap['a']=50; mymap['b']=100; mymap['c']=150; mymap['d']=200; it = mymap.find('b'); if (it != mymap.end()) mymap.erase (it); // print content: std::cout << "elements in mymap:" << '\n'; std::cout << "a => " << mymap.find('a')->second << '\n'; std::cout << "c => " << mymap.find('c')->second << '\n'; std::cout << "d => " << mymap.find('d')->second << '\n'; return 0; }
运行结果:
elements in mymap:
a => 50
c => 150
d => 200
map中的swap
map中的swap是两个容器的交换。#include <map> #include <iostream> using namespace std; int main( ) { map <int, int> m1, m2, m3; map <int, int>::iterator m1_Iter; m1.insert ( pair <int, int> ( 1, 10 ) ); m1.insert ( pair <int, int> ( 2, 20 ) ); m1.insert ( pair <int, int> ( 3, 30 ) ); m2.insert ( pair <int, int> ( 10, 100 ) ); m2.insert ( pair <int, int> ( 20, 200 ) ); m3.insert ( pair <int, int> ( 30, 300 ) ); cout << "The original map m1 is:"; for ( m1_Iter = m1.begin( ); m1_Iter != m1.end( ); m1_Iter++ ) cout << " " << m1_Iter->second; cout << "." << endl; // This is the member function version of swap //m2 is said to be the argument map; m1 the target map m1.swap( m2 ); cout << "After swapping with m2, map m1 is:"; for ( m1_Iter = m1.begin( ); m1_Iter != m1.end( ); m1_Iter++ ) cout << " " << m1_Iter -> second; cout << "." << endl; cout << "After swapping with m2, map m2 is:"; for ( m1_Iter = m2.begin( ); m1_Iter != m2.end( ); m1_Iter++ ) cout << " " << m1_Iter -> second; cout << "." << endl; // This is the specialized template version of swap swap( m1, m3 ); cout << "After swapping with m3, map m1 is:"; for ( m1_Iter = m1.begin( ); m1_Iter != m1.end( ); m1_Iter++ ) cout << " " << m1_Iter -> second; cout << "." << endl; system("pause"); }
运行结果如下:
map的一些其他函数
empty() 如果map为空则返回trueget_allocator() 返回map的配置器
key_comp() 返回比较元素key的函数
lower_bound() 返回键值>=给定元素的第一个位置
upper_bound() 返回键值>给定元素的第一个位置
size() 返回map中元素的个数
multimap
multimap中的键也是按照构造函数中所指定的二元谓词进行排序的。multimap的元素类型和map是一致的,这里就不在赘述。
这里就简要概述一下multimap和map不同的地方:multimap中相同的键可以多次出现,而不像map只能出现一次。
在multimap中没有定义[]运算符,当然也没有定义at()成员函数,因此,multimap进行插入的时候,只能利用insert()函数进行插入。
相关文章推荐
- 使用C++实现JNI接口需要注意的事项
- android Google Map获取地理位置信息的方法
- Spark RDD API详解(一) Map和Reduce
- Python中map()函数浅析
- 关于指针的一些事情
- Android使用Google Map浅谈
- c++ primer 第五版 笔记前言
- share_ptr的几个注意点
- Lua中调用C++函数示例
- Lua教程(一):在C++中嵌入Lua脚本
- Lua教程(二):C++和Lua相互传递数据示例
- C++联合体转换成C#结构的实现方法
- Erlang中的映射组Map详细介绍
- C++高级程序员成长之路
- C++编写简单的打靶游戏
- C++ 自定义控件的移植问题
- C++变位词问题分析
- C/C++数据对齐详细解析
- C++基于栈实现铁轨问题
- C++中引用的使用总结