今天做的四道题都和哈希表相关。
思路其实是不难的,但是实际上操作起来的时候会发现stl很多容器用的不熟练,需要增强对set和map的掌握。
力扣题目链接:242.有效的字母异位词
给定两个字符串 s 和 t ,编写一个函数来判断 t 是否是 s 的字母异位词。
示例 1: 输入: s = "anagram", t = "nagaram" 输出: true
示例 2: 输入: s = "rat", t = "car" 输出: false
这道题的思路倒是不复杂,说白了就是判断两个字符串里各字母出现的次数是否相等。
class Solution {
public:
bool isAnagram(string s, string t) {
int record[26] = { 0 };
for (int i = 0; i < s.length(); i++) {
record[s[i] - 'a']++;
}
for (int i = 0; i < t.length(); i++) {
if (record[t[i] - 'a'] == 0) {
return false;
}
record[t[i] - 'a']--;
}
for (int i = 0; i < 26; i++) {
if (record[i] != 0) {
return false;
}
}
return true;
}
};
此外,学习了后面的题目之后尝试着使用了一下用unordered_map容器来做,也能够顺利实现功能。
class Solution {
public:
bool isAnagram(string s, string t) {
unordered_map map;
for (int i = 0; i < s.length(); i++) {
auto iter = map.find(s[i]);
if (iter != map.end()) {
iter->second++;
}
else {
map.insert(pair(s[i], 1));
}
}
for (int i = 0; i < t.length(); i++) {
auto iter = map.find(t[i]);
if (iter == map.end()) return false;
else {
if (iter->second == 0) {
return false;
}
else {
iter->second--;
}
}
}
for (auto iter = map.begin(); iter != map.end(); ++iter) {
if (iter->second) {
return false;
}
}
return true;
}
};
不过使用这些容器的时候还有一些问题,具体的放在后面的题目细说。
力扣题目链接:349. 两个数组的交集
给定两个数组,编写一个函数来计算它们的交集。
这一题乍一看思路还是比较简单的,使用set容器记录情况就可以了。
但是实际写起代码的时候还是遇到了一些困难。
class Solution {
public:
vector intersection(vector& nums1, vector& nums2) {
unordered_set result_set;
unordered_set nums_set(nums1.begin(), nums1.end());
for (int num : nums2) {
if (nums_set.find(num) != nums_set.end()) {
result_set.insert(num);
}
}
return vector(result_set.begin(), result_set.end());
}
};
力扣题目链接:第202题. 快乐数
编写一个算法来判断一个数 n 是不是快乐数。
「快乐数」定义为:对于一个正整数,每一次将该数替换为它每个位置上的数字的平方和,然后重复这个过程直到这个数变为 1,也可能是 无限循环 但始终变不到 1。如果 可以变为 1,那么这个数就是快乐数。
如果 n 是快乐数就返回 True ;不是,则返回 False 。
快乐数重要的是他执行了一系列运算之后是否能化为1,如果不能化为1的话一定会在某一步开始循环。那我们就只需要记录它各个过程化为的数字,如果这个数字在后续重复出现那就说明不是快乐数了。
class Solution {
public:
bool isHappy(int n) {
unordered_set result_set;
int tmp;
while (true) {
tmp = 0;
while (n) {
tmp += (n % 10) * (n % 10);
n /= 10;
}
if (tmp == 1) return true;
if (result_set.find(tmp) != result_set.end()) {
return false;
}
result_set.insert(tmp);
n = tmp;
}
}
};
力扣题目链接:1. 两数之和
给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。
构建一个哈希表一步步记录nums里各数的值和对应的数组下标,然后寻找看看是否已经记录过target - nums,如果有的话就返回他们的数组下标。
class Solution {
public:
vector twoSum(vector& nums, int target) {
unordered_map map;
for (int i = 0; i < nums.size(); i++) {
if (map.find(target - nums[i]) != map.end()) {
return{ map.find(target - nums[i])->second, i };
}
map.insert(pair(nums[i], i));
}
return {};
}
};
可以优化的地方: