文章目录
1 题目
2 思路
如果直接暴力求解,两个for循环,内存循环和外层循环遍历的数字相加,然后判断值是否等于target,但是时间复杂度为O(n^2)
,如果这样写是超时的。
法1:
- 1,首先使用哈希表
map<string, int>
存储向量(变长数组)中每个值的位置,如果遇到两个值相同的情况,就判断2倍的值是否等于target,不等时,继续存储,直至全部存入哈希表中【记录排序前的元素位置】; - 2,对向量进行增量排序;
- 3,逆向遍历排序后的向量,每遍历一个元素时,让它和内层从头遍历的元素累加,判断是否等于target【最坏的情况,target的两个因子刚好是最中间的两个元素,那时间复杂度也为
O(n^2/4)
】;
法2:
- 1,使用哈希表
map<string, int>
存储向量(变长数组)中每个值的位置,如果遇到两个值相同的情况,就判断2倍的值是否等于target,不等时,继续存储,直至全部存入哈希表中【方便后面直接求target - 因子1
的元素位置】; - 2,遍历哈希表,依次判断
target - 因子1(key)
的键值是否存在,如果存在就输出。
3 代码
3.1 法一
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
vector<int> ans;
map<string, int> hash;
for(int i = 0; i < nums.size(); i++){
map<string, int>::iterator findIter = hash.find(to_string(nums[i]));
if(findIter == hash.end()){
hash[to_string(nums[i])] = i;
}else{
if(nums[i] * 2 == target){
ans.push_back(findIter->second);
ans.push_back(i);
return ans;
}
}
}
sort(nums.begin(), nums.end());
for(int i = nums.size() - 1; i >= 0; i--){
if(ans.size() > 0) break;
for(int j = 0;j < i; j++){
if(nums[i] + nums[j] == target){
ans.push_back(hash[to_string(nums[j])]);
ans.push_back(hash[to_string(nums[i])]);
break;
}else if (nums[i] + nums[j] > target){
break;
}else{}
}
}
return ans;
}
};
3.2 法2
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
vector<int> ans;
unordered_map<string, int> hash;
for(int i = 0; i < nums.size(); i++){
unordered_map<string, int>::iterator findIter = hash.find(to_string(nums[i]));
if(findIter == hash.end()){
hash[to_string(nums[i])] = i;
}else{//特殊处理target的两个因子的值相同的情况
if(nums[i] * 2 == target){
ans.push_back(findIter->second);
ans.push_back(i);
return ans;
}
}
}
for (unordered_map<string, int>::iterator iter = hash.begin();iter != hash.end();iter++){
unordered_map<string, int>::iterator findIter = hash.find(to_string(target - stoi(iter->first)));
if(findIter != hash.end() && findIter != iter){//key存在,并且不是同一个key
// cout<<"iter:"<<iter->first<<" "<<iter->second<<endl;
// cout<<"findIter:"<<findIter->first<<" "<<findIter->second<<endl;
ans.push_back(iter->second);
ans.push_back(findIter->second);
return ans;
}
}
// sort(nums.begin(), nums.end());
// for(int i = nums.size() - 1; i >= 0; i--){
// if(ans.size() > 0) break;
// for(int j = 0;j < i; j++){
// if(nums[i] + nums[j] == target){
// ans.push_back(hash[to_string(nums[j])]);
// ans.push_back(hash[to_string(nums[i])]);
// break;
// }else if (nums[i] + nums[j] > target){
// break;
// }else{}
// }
// }
return ans;
}
};