题目一
我的想法
定义一个长度为26的数组,对应26个小写字母
遍历s,在每个字母对应的位置+1。遍历s结束后,数组中存字符串s放字母出现次数。
遍历t,在每个字母对应的位置 - 1。
最后检查数组,如果每个数都是0,则是互为字母异位,否则不满足。
代码
class Solution {
public:
bool isAnagram(string s, string t) {
int record[26] = { 0 };
for (int i = 0; i < s.size(); i++)
record[s[i] - 'a']++;
for (int i = 0; i < t.size(); i++)
record[t[i] - 'a']--;
for (int i = 0; i < 26; i++)
if (record[i] != 0)
return false;
return true;
}
};
题目二
我的想法
定义一个长度为1000的数组,对应数字元素0~1000,数组初始化为0。
数组值为0表示没有该元素,为1表示有该数,为2表示该位置已经发生过一次冲突。
遍历nums1,在元素对应的数组的位置标志1。
遍历结束之后就在数组中标记了nums1有的元素。
遍历nums2,若元素对应的数组值为1,即发生冲突,则把该元素加入结果数组,并标记为2。
解析思路
若用数组,则会造成很大的空间浪费,将数组换成结构体set。
数组和c++中set结构体的区别。
代码
class Solution2 {
public:
vector<int> intersection(vector<int>& nums1, vector<int>& nums2) {
unordered_set<int> result_set;
unordered_set<int> nums_set(nums1.begin(), nums1.end());
//遍历nums2中的元素
for (int num : nums2) {
//如果在数组1中找到当前遍历到的数组2的元素
if (nums_set.find(num) != nums_set.end()) {
result_set.insert(num);
}
}
return vector<int>(result_set.begin(), result_set.end());
}
};
题目三
我的想法
只有当某一步得出的数首位为1,其余位都是0的时候,才满足快乐数。
可以从最开始的数开始进行计算并装填哈希表,一旦发生冲突,说明有死循环,返回false。
代码
class Solution {
public:
bool isHappy(int n) {
unordered_set<int> set;
while (1) {
int sum = 0;
while (n) {
sum += (n % 10) * (n % 10);
n /= 10;
}
if (sum == 1)
return true;
if (set.find(sum) != set.end())
return false;
else
set.insert(sum);
n = sum;
}
}
};
题目四
我的想法
暴力法, 双重循环,外层遍历,作为一个加数,内层作为另一个加数,如果相加为目标值则可直接返回数组下标。
解析
使用map作哈希表,则仅需一层循环即可。
map和数组、set的区别:
数组大小固定,数据少会造成内存浪费。
set是一个集合,只存数值,没有记录下标,不符合本题要求。
本题map中,元素作为键,对应的下标作为值。
代码
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
unordered_map<int, int >map;
for (int i = 0; i < nums.size(); i++) {
auto iter = map.find(target - nums[i]);
if (iter != map.end())
return { iter->second,i };
map.insert(pair<int, int >(nums[i], i));
}
return {};
}
};