1002. 查找常用字符
题意:
给定仅有小写字母组成的字符串数组 A,返回列表中的每个字符串中都显示的全部字符(包括重复字符)组成的列表。例如,如果一个字符在每个字符串中出现 3 次,但不是 4 次,则需要在最终答案中包含该字符 3 次。
你可以按任意顺序返回答案。
示例 1:
输入:["bella","label","roller"]
输出:["e","l","l"]
示例 2:
输入:["cool","lock","cook"]
输出:["c","o"]
第一种解题思路:
第一种解法:
- 需要用到两个map容器,第一个map存第一个字符串出现的字母,第二个字符全部设置为0
- 循环从第二个字符串开始,每一个字符串都把字符存入map容器中
- 然后跟第一个容器比较小,取小的值(如果后面不出现的字符那么一定为0),直到最后一个字符串
- 遍历第一个map容器,就是我们需要的结果
优点:简单,易懂.
缺点:时间复杂度太高,运行时间惨不忍睹…
代码:
class Solution {
public:
vector<string> commonChars(vector<string>& words) {
if(words.size() == 0)
return {};
map<string, int> hash;
map<string, int>map;
vector<string> res;
for (auto c : words[0])
{
string d(1, c);
++map[d];
}
for (int i = 1; i < words.size();i++)
{
string str = words[i];
hash.clear();
for (const char c : str)
{
string b(1, c);
++hash[b];
}
for (const char c : words[0])
{
string b(1, c);
map[b] = min(map[b], hash[b]);
}
}
for (auto it = map.begin();it != map.end();it++)
{
for (int i = 0; i < it->second; i++)
{
res.push_back(it->first);
}
}
return res;
}
};
运行结果:
第二种解法思路
其实并不能算新的解题思路,就是在原来的基础上做改进.
- 把map容器换为26个字母的数组,静态数组速度比较快
代码:
class Solution {
public:
vector<string> commonChars(vector<string>& words) {
if(words.size() == 0)
return {};
int map[26] = { 0 };
for (auto c : words[0])
{
++map[c - 97];
}
for (int i = 1; i < words.size();i++)
{
int hash[26] = { 0 };
string str = words[i];
for (const char c : str)
{
++hash[c - 97];
}
for (const char c : words[0])
{
map[c - 97] = min(map[c - 97], hash[c - 97]);
}
}
vector<string> res;
for (int i = 0; i < 26; i++)
{
for (int j = 0; j < map[i]; j++)
{
res.emplace_back(1, i + 'a');
}
}
return res;
}
};
数组运行结果:
把数组改为vector后运行结果:
总结:
这道题我尝试了很多中方法来降低时间,但是都没成功,我最少的都是8ms.后来把数组改为vector容器,运行时间是一样的,就是空间减少了点,是因为我用数组时清0比较麻烦,所有我直接在每一次循环体都重新定义了一个数组,这样省去清0的麻烦.