This commit is contained in:
2022-12-03 10:38:05 +08:00
parent 94c4c84da5
commit e552116d76
6 changed files with 141 additions and 0 deletions

View File

@@ -12,6 +12,11 @@
- [总结](./linked_list.md)
- [环形链表](./linked_list_cycle.md)
# 哈希表
- [总结](./hash_table.md)
- [四数相加 II](./four_sum_ii.md)
# 字符串
- [总结](./string.md)

11
notes/src/four_sum_ii.md Normal file
View File

@@ -0,0 +1,11 @@
# 四数相加 II
[Leetcode](https://leetcode.com/problems/4sum-ii/)
这是一道经典的哈希表的题。
双重循环遍历 A 和 B ,把 `A[i] + B[j]` 作为 key ,把出现的次数作为 value 。
同样地遍历 C 和 D 。
那么现在就得到了两个哈希表了,遍历哈希表,看看是否有两个值之和为 0 ,如果有的话统计出现的次数。

56
notes/src/hash_table.md Normal file
View File

@@ -0,0 +1,56 @@
# 总结
当我们需要判断某个元素是否出现过时,考虑用哈希表。
## unordered_map 与 unordered_set
这俩的底层都是用哈希函数实现的,因此访问其中的元素可以达到 O(1) 的时间复杂度。
它们的区别在于unordered_map 存储的是 key-value ,而 unordered_set 只存储 key 。
一般我们直接用 unordered_map 就可以完成所有操作了。
常见用法:
```cpp
#include <iostream>
#include <string>
#include <unordered_map>
int main(int argc, const char *argv[]) {
// key 为 std::string 类型的value 为 int 类型的
std::unordered_map<std::string, int> map;
// 插入
map["foo"] = 1;
map["bar"] = 2;
map["non"] = 3;
// 访问
std::cout << map["foo"] << std::endl;
// 删除
map.erase("foo");
// 判断元素是否存在
if (map.count("bar") > 0) {
std::cout << "Exist" << std::endl;
} else {
std::cout << "Not exist" << std::endl;
}
// 另一种判断元素是否存在的方法
// find() 会返回元素的正向迭代器,如果没找到则返回 end()
if (map.find("bar") != map.end()) {
std::cout << "Exist" << std::endl;
} else {
std::cout << "Not exist" << std::endl;
}
// 合并两个 unordered_map
std::unordered_map<std::string, int> newMap;
newMap["microsoft"] = 1;
newMap["surface"] = 1;
map.insert(newMap.begin(), newMap.end());
// 遍历
for (std::unordered_map<std::string, int>::iterator iter = map.begin();
iter != map.end(); ++iter) {
std::cout << iter->first << iter->second << std::endl;
}
return 0;
}
```