C++ STL 容器之 map

map 是 C++ 对数据结构哈希表的实现。要使用 map,请在程序头添加:

#include <map>
using name space std;

数组是最基础的也是我们使用得最为频繁的容器。但数组只能提供数值到其他类型值的映射,即数组只能使用数值作为索引的。很多时候我们需要以其他类型作为索引,如 char 或者 string 等。map 正好可以满足这种需求,故 map 对象的创建需要指定 index 和 value 两个值的类型,即
map<index, value> m;
map 的 index 可以是各种不同的类型,如 int、char 、string 等。map 中的元素是按照 index 的升排列的,也不允许存在具有相同 index 值的元素。

map 对象的定义与初始化

map<int, char> m; 创建一个空 map 容器
map<int, char> m1(m); m1 = m
map<int, char> m1 = m m1 = m
map<int, char> m({ {1, 'a'}, {3, 'c'} });
map<int, char> m = { {1, 'a'}, {3, 'c'} };

向 map 对象添加元素

作为一种关联容器,map 中的元素是根据关键字存储的,故 map 不支持类似于顺序容器中的与位置相关的操作,如 .push_front、.push_back 等。在向 map 对象中添加元素时,只需要指明带插入的元素本身,而元素插入的位置由 map 根据其关键字自行决定。

使用 insert 插入元素

插入单个元素

map<int, char> m = { {1, 'a'}, {2, 'b'} };
m.insert({3, 'c'}); // m = { {1, 'a'}, {2, 'b'}, {3, 'c'} };

插入一段元素

map<int, char> m = { {1, 'a'}, {2, 'b'} };
map<int, char> m1 = { {3, 'c'} };
m1.insert(m.begin(), m.end()); // m = { {1, 'a'}, {2, 'b'}, {3, 'c'} };

注意,这里要求提供元素的容器和插入元素的容器的元素类型是相容的,而不要求两个容器的类型是相同的。下面这样是允许的:

vector<pair<int, int>> v = { {1, 'a'}, {2, 'b'}, {3, 'c'} };
map<int, char> m1;
m1.insert(v.begin(), v.end()); // m = { {1, 'a'}, {2, 'b'}, {3, 'c'} };

在上面这段代码中,尽管容器 v 和 容器 m 的容器类型不同(vector 与 map),但 v 的元素类型是 pair<int, int> 而 m 的元素类型是 pair<int, char>,int 和 char 又是可以互相转换的(即已存在内置的转关方法),故这个插入操作是成功的。

检测 insert 的返回值
map 的 .insert 方法会返回一个 pair 对象,第一个成员是一个迭代器,指向插入的元素在 map 中的位置;第二个成员时一个 bool 变量。若插入元素成功,此 bool 变量的值为 true,否则为 false。

删除 map 中的元素

使用 .erase 删除 map 中的关键字,这里 .erase 有三个重载的版本:

m.erase(k) 指定关键字 k,删除 m 中关键字为 k 的所有元素
m.erase(p) 指定迭代器 p,删除 m 中由迭代器 p 指向的元素
m.erase(b, e) 删除 m 中有迭代器返回 [b, e) 指示范围内的所有元素

.erase 函数会返回实际删除的元素的个数。(对 map 来说,只可能返回 0 或 1,返回 0 即意味着 m 中原本不存在要删除的元素)

访问 map 中的元素

使用下标访问

像数组一样,map 支持下标随机访问

map<char, int> m = { {'a', 1},{'b', 2},{'c', 3} };
cout << m['a']; // 输出:1

注意:当欲访问的关键字并不在 map 中时,map 会自动地添加一个具有该关键字值的元素,如

map<char, int> m = { {'a', 1},{'b', 2},{'c', 3} };
m['a'] = 1;
m['b'] = 2;
m['c'] = 3; // m = { {'a', 1},{'b', 2},{'c', 3} };

如果不想使用 map 的这一特性,可是使用 .at 方法来代替下标操作

map<char, int> m = { {'a', 1},{'b', 2} };
m.at('c') = 3; //error!m 中没有关键字为 'c' 的元素

使用迭代器进行访问

使用迭代器访问 map 中的元素时需要注意,map 的元素是一个 pair

map<char, int> m = { {'a', 1},{'b', 2},{'c', 3} };
//将 dp 中值为奇数的元素置为 0
for (auto it=m.begin(); it!=m.end(); it++) {
    if (it->second % 2)
    	cout << it->first << " "}
// 输出:a c

使用 C++ 11 新特性访问

map<char, int> m = { {'a', 1},{'b', 2},{'c', 3} };
//将 dp 中值为奇数的元素置为 0
for (auto e : m) {
    if (e.second % 2)
    	cout << e.first << " "}
// 输出:a c

注意:这种方式得到的 e 是 m 中元素的拷贝,若想要得到 m 中元素的本身,请使用 &
for (auto &e:m)

使用 .find 检查一个元素是否在 map 中

很多时候我们只是关心 map 中是否存在具有某个关键字的元素。这是可以使用
m.find(k)
来获取 map 中第一个关键字为 k 的元素的迭代器。若 map 中不存在这样的元素,则 .find 返回的是尾后迭代器。故使用一下代码即可检查 map 中是否具有关键字为 k 的元素
if (m.find(k)!=m.end())

猜你喜欢

转载自blog.csdn.net/qq_38479159/article/details/82828900